You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
<h2id="paso-5-construcción-de-rutas"><aclass="anchor" href="#paso-5-construcción-de-rutas"></a>Paso 5: Construcción de Rutas</h2>
697
+
<divclass="sectionbody">
698
+
<divclass="paragraph">
699
+
<p>Esta API tendrá dos rutas principales:</p>
700
+
</div>
701
+
<divclass="ulist">
702
+
<ul>
703
+
<li>
704
+
<p><code>/api/quotes/</code>: Lista todas las citas disponibles.</p>
705
+
</li>
706
+
<li>
707
+
<p><code>/api/quotes/random</code>: Lista una cita aleatoria.</p>
708
+
</li>
709
+
</ul>
710
+
</div>
711
+
<divclass="paragraph">
712
+
<p>Para esto se debe editar el <code>router</code> ubicado en <code>lib/stoic_quotes_web/router.ex</code>.</p>
713
+
</div>
714
+
<divclass="listingblock">
715
+
<divclass="content">
716
+
<preclass="highlightjs highlight"><codeclass="language-elixir hljs" data-lang="elixir">scope "/api", StoicQuotesWeb do
717
+
pipe_through :api
718
+
get "/quotes", QuotesController, :index
719
+
get "/quotes/random", QuotesController, :show
720
+
end</code></pre>
721
+
</div>
722
+
</div>
723
+
<divclass="paragraph">
724
+
<p>El siguiente código nos indica lo siguiente:</p>
725
+
</div>
726
+
<divclass="ulist">
727
+
<ul>
728
+
<li>
729
+
<p><code>scope</code>: Es una macro que acepta como parámetro la ruta base (endpoint) y el módulo base para buscar los controladores.</p>
730
+
</li>
731
+
</ul>
732
+
</div>
733
+
<divclass="listingblock">
734
+
<divclass="content">
735
+
<preclass="highlightjs highlight"><codeclass="language-elixir hljs" data-lang="elixir"># las rutas tendrán como base /api y como base el módulo StoicQuotesWeb
736
+
scope "/api", StoicQuotesWeb do</code></pre>
737
+
</div>
738
+
</div>
739
+
<divclass="paragraph">
740
+
<p>El siguiente código nos indica lo siguiente:</p>
741
+
</div>
742
+
<divclass="ulist">
743
+
<ul>
744
+
<li>
745
+
<p><code>pipe_through</code>: Es una macro que gatillará lo definido en el pipeline <code>:api</code> para todos los requests que cumplan el <code>scope "/api"</code>.</p>
<p>El pipeline de <code>:api</code> establece un pipeline para aceptar requests del formato <code>json</code>,
756
+
se define como lo siguiente:</p>
757
+
</div>
758
+
<divclass="listingblock">
759
+
<divclass="content">
760
+
<preclass="highlightjs highlight"><codeclass="language-elixir hljs" data-lang="elixir">pipeline :api do
761
+
plug(:accepts, ["json"])
762
+
end</code></pre>
763
+
</div>
764
+
</div>
765
+
<divclass="paragraph">
766
+
<p>El código nos indica lo siguiente:</p>
767
+
</div>
768
+
<divclass="ulist">
769
+
<ul>
770
+
<li>
771
+
<p><code>get</code>: Es la función identificada con el verbo HTTP a usar en la ruta. Por ejemplo si usamos <em>POST</em> no encontrará la ruta.</p>
772
+
</li>
773
+
<li>
774
+
<p><code>/quotes</code>: Es la ruta donde deberemos hacer las llamadas HTTP. Como estamos dentro del scope <code>/api/</code> la ruta completa será <code>/api/quotes</code></p>
775
+
</li>
776
+
<li>
777
+
<p><code>QuotesController</code>: Es el módulo donde se encontrarán las funciones para procesar el request. Como estamos dentro del scope <code>StoicQuotesWeb</code> el módulo usado será <code>StoicQuotesWeb.QuotesController</code>.</p>
778
+
</li>
779
+
<li>
780
+
<p><code>:index</code>: Es un átomo que permite identificar el request, utilizado en el módulo para segregar las funcionalidad de manejar el request. En este caso se asociará a una función dentro del controlador llamada <code>index</code>.</p>
781
+
</li>
782
+
</ul>
783
+
</div>
784
+
<divclass="listingblock">
785
+
<divclass="content">
786
+
<preclass="highlightjs highlight"><codeclass="language-elixir hljs" data-lang="elixir"># verbo http, "/ruta", modulo, parámetro
787
+
get "/quotes", QuotesController, :index</code></pre>
<h2id="paso-6-crear-el-controlador"><aclass="anchor" href="#paso-6-crear-el-controlador"></a>Paso 6: Crear el controlador</h2>
847
+
<divclass="sectionbody">
848
+
<divclass="paragraph">
849
+
<p>El <ahref="https://hexdocs.pm/phoenix/controllers.html#actions">controlador</a> es donde se alojan las funciones que responderán a las requests definidas en el router.
850
+
Por lo que se debe crear un nuevo archivo llamado <code>quotes_controller.ex</code> dentro de <code>stoic_quotes_web/controllers/quotes_controller.ex</code>
<preclass="highlightjs highlight"><codeclass="language-elixir hljs" data-lang="elixir">defmodule StoicQuotesWeb.QuotesController do
857
+
use Phoenix.Controller, formats: [:json]
858
+
alias StoicQuotes.Quotes
859
+
860
+
def index(conn, _params) do
861
+
quotes = %{quotes: Quotes.list_quotes()}
862
+
render(conn, :index, quotes)
863
+
end
864
+
865
+
def show(conn, _params) do
866
+
quote = %{quote: Quotes.get_random_quote()}
867
+
render(conn, :show, quote)
868
+
end
869
+
end</code></pre>
870
+
</div>
871
+
</div>
872
+
<divclass="ulist">
873
+
<ul>
874
+
<li>
875
+
<p><code>def index(conn, _params)</code>: Notar como cada función recibe un parámetro conexión (conn), donde tiene los detalles del request, el cual se usará para ser enviado a otras funciones como <code>render</code> y el resto de parámetros (params) donde se reciben los distintos parámetros definidos en la ruta principal.</p>
876
+
</li>
877
+
<li>
878
+
<p><code>use Phoenix.Controller, formats: [:json]</code>: Define a este módulo como un controlador que responde con <code>json</code>.</p>
879
+
</li>
880
+
<li>
881
+
<p><code>render(conn, :index, quotes)</code>: Utiliza la <ahref="https://hexdocs.pm/phoenix/Phoenix.Controller.html#module-rendering-and-layouts">función render</a> que llama a la vista y genera el json final pasándole los parámetros desde el controlador.</p>
882
+
</li>
883
+
</ul>
884
+
</div>
885
+
</div>
886
+
</div>
887
+
<divclass="sect1">
888
+
<h2id="paso-7-crear-la-vista"><aclass="anchor" href="#paso-7-crear-la-vista"></a>Paso 7: Crear la vista</h2>
889
+
<divclass="sectionbody">
890
+
<divclass="paragraph">
891
+
<p>La vista será principalmente un <code>json</code>, por lo que tenemos que crear un nuevo archivo llamado <code>quotes_json.ex</code>
892
+
dentro del mismo directorio que <code>quotes_controller.ex</code>.</p>
893
+
</div>
894
+
<divclass="paragraph">
895
+
<p>Notar que tiene las mismas funciones usadas en el controlador, con la excepción de que definen su parámetro
896
+
como el dato a mostrar, que es pasado a la función <code>render</code> usada en el controlador.</p>
897
+
</div>
898
+
<divclass="listingblock">
899
+
<divclass="content">
900
+
<preclass="highlightjs highlight"><codeclass="language-elixir hljs" data-lang="elixir">defmodule StoicQuotesWeb.QuotesJSON do
901
+
alias StoicQuotes.Quotes.Quote
902
+
903
+
def index(%{quotes: quotes}) do
904
+
%{data: for(quote <- quotes, do: data(quote))}
905
+
end
906
+
907
+
def show(%{quote: quote}) do
908
+
%{data: data(quote)}
909
+
end
910
+
911
+
defp data(%Quote{} = datum) do
912
+
%{
913
+
quote: datum.quote,
914
+
author: datum.author,
915
+
source: datum.source
916
+
}
917
+
end
918
+
end</code></pre>
919
+
</div>
920
+
</div>
921
+
</div>
922
+
</div>
923
+
<divclass="sect1">
924
+
<h2id="paso-8-modificar-el-contexto"><aclass="anchor" href="#paso-8-modificar-el-contexto"></a>Paso 8: Modificar el contexto</h2>
925
+
<divclass="sectionbody">
926
+
<divclass="paragraph">
927
+
<p>Debemos modificar el contexto (o modelo) para añadir la función <code>Quotes.get_random_quote()</code> usada en el controlador
{"data":[{"author":"Marcus Aurelius","source":"Book II, Meditations","quote":"Seldom are any found unhappy from not observing what is in the minds of others. But such as observe not well the stirrings of their own souls must of necessity be unhappy."},{"author":"Marcus Aurelius","source":"Book XI, Meditations","quote":"Consider whence each thing came, of what it was compounded, into what it will be changed, how it will be with it when changed, and that it will suffer no evil."},{"author":"Marcus Aurelius","source":"Book X, Meditations","quote":"Accustom yourself as much as possible, when any one takes any action, to consider only: To what end is he working? But begin at home; and examine yourself first of all."}]}%</code></pre>
0 commit comments