Hi, I’m new to Elixir and Phoenix so far the support/community and language has been great. I’m still reading the docs and starting to understand everything but one thing I can’t find is the correct way to do conditional template/views loading.
In my app I’m using two different HTML themes ones for the public static website and one for the user admin or dashboard, when I user is logged in I would like to use the specific theme so I need to load a different app.html.eex how can this be done?
You might add a plug somewhere in your pipeline (router or endpoin.ex) which would assign a template or a whole view based on the user data.
It would be something like this
In the router (or endpoint):
def MyApp.Router do
use Phoenix.Router
pipeline :browser do # or any other pipeline
# ...
# the options [admin: ..., user: ...] I just picked as an example
plug(MyApp.Plugs.Theme, [admin: "admin.html.eex", user: "app.html.eex"])
# ...
end
end
Then you can create a new folder under your /lib to put your custom plugs in (like /lib/plugs) and create a theme.ex plug there:
defmodule MyApp.Plugs.Theme do
@moduledoc "Assings a theme to the connection based on current user."
import Phoenix.Controller, only: [put_layout: 2]
# just an example how to init options in plug
def init(opts) do
admin_theme = opts[:admin]
user_theme = opts[:user]
{admin_theme, user_theme}
end
def call(%Plug.Conn{assigns: assigns} = conn, {admin_theme, user_theme}) do
# :admin? would be replaced with your own assign that defines whether the
# current user is an admin
# maybe you can use https://hexdocs.pm/coherence/Coherence.html#current_user/1 instead
if assigns[:admin?] do
put_layout(conn, admin_theme)
else
put_layout(conn, user_theme)
end
end
end