Routing

Start postgres:

docker run --name postgres -p 5432:5432 -e POSTGRES_PASSWORD=postgres -d postgres

Create a new project:

mix phx.new app1 --live
cd app1
mix ecto.create
mix phx.server

Take a look at router.ex:

defmodule App1Web.Router do
  use App1Web, :router

  pipeline :browser do
    plug :accepts, ["html"]
    plug :fetch_session
    plug :fetch_live_flash
    plug :put_root_layout, html: {App1Web.Layouts, :root}
    plug :protect_from_forgery
    plug :put_secure_browser_headers
  end

  pipeline :api do
    plug :accepts, ["json"]
  end

  scope "/", App1Web do
    pipe_through :browser
    get "/", PageController, :home
  end
end

use App1Web, :router

This will inject some code defined in app1_web.ex in to current Router module:

defmodule App1Web do
  # ...
  def router do
    quote do
      use Phoenix.Router, helpers: false
      import Plug.Conn
      import Phoenix.Controller
      import Phoenix.LiveView.Router
    end
  end
  # ...
end

pipeline & plug

pipeline and plug come from Plug, which is Phoenix's middleware mechanism.

A Plug manipulates a connection, in other languages and frameworks middleware usually manipulates Request and Response.

A Plug can be a function or a module. Let's take module as an example:

defmodule App1Web.Plugs.SayHello do
  import Plug.Conn

  def init(default), do:
    IO.puts "SayHello Plug is Ready"
  end

  def call(conn, _opts) do
    IO.puts "Hello from the plug!"
    Plug.Conn.put_resp_header(conn, "x-say-hello", "Hello")
    conn
  end
end

And obviously a pipeline is a collection of middlewares. Insert the middleware to the top of the list:

  pipeline :browser do
    plug App1Web.Plugs.SayHello
    # ...
  end

It is worth mentioning that Phoenix provides compile-time checked verified routes. Errors such as misspelled route names or incorrect parameters when generating paths/URLs will be caught by the compiler.