travisf
I am working on converting an existing application to a multi-tenant one with subdomains enforcing the organization. Tenants have an “admin” panel but can also impersonate their own customers via an impersonator session.
The impersonator session takes a token (decoded with Guardian) adds information about the organization and the impersonator to the session and then redirects to the storefront.
The way the app is setup a redirect from admin to the storefront takes one from localhost:4000 to localhost:4002.
For now I’m just playing with this locally so this isn’t an infrastructure question, per se, but if I redirect from a tenant admin, say customer1.localhost:4000 I loose the subdomain going to localhost:4002. Is there something in the endpoint or a plug I could implement to enforce the subdomain while the impersonation finishes?
For reference:
The AdminApp.ImpersonatonController looks like this (modified for brevity):
def impersonate(%Conn{} = conn, %{} = params) do
impersonator = Guardian.Plug.current_resource(conn)
org_id = Repo.get_org_id()
claims = %{
impersonator_id: impersonator.id,
organization: org_id
}
{_, token, _claims} = Guardian.encode_and_sign(impersonator, claims)
conn
|> authorize(action: :impersonate)
|> redirect(external: "#{url}/impersonate?token=#{token}))
end
Then the StorefrontWeb.SessionController has this action:
def impersonate(conn, %{"token" => impersonation_token}) do
conn
|> ... decode and verify token...
|> create_impersonator_session()
end
defp create_impersonator_session({:ok, token, conn}) do
organization = token["organization"]
conn =
conn
|> GuardianPlug.sign_in(user)
|> put_session(:impersonating, {token["impersonator_id"], token["user_id"]})
|> put_session(:organization, organization)
redirect(conn, to: successful_sign_in_redirect_path(conn, user))
end
Trending in Questions
Other Trending Topics
Categories:
Sub Categories:
Forums
Popular Tags
- #ecto
- #liveview
- #troubleshooting
- #learning-elixir
- #deployment
- #library
- #erlang
- #testing
- #genserver
- #mix
- #absinthe
- #remote-other
- #otp
- #plug
- #how-to-question
- #macros
- #postgres
- #channels
- #elixirconf
- #exunit
- #discussion
- #code-sync
- #javascript
- #podcasts
- #onsite
- #dialyzer
- #docker
- #authentication
- #umbrella
- #full-time-contract
- #podcasts-by-brainlid
- #ecto-query
- #elixir-ls
- #blog-post
- #phoenix_html
- #iex
- #graphql
- #ai
- #genstage
- #elixirconf-us
- #websockets
- #supervisor
- #advent-of-code
- #distillery
- #processes
- #api
- #forms
- #metaprogramming
- #security
- #hex











Showing Posts 1 to 4- Show Best Posts
- Show All Posts (oldest first)
- Show All Posts (newest first)
sodapopcan
The subdomain is stored in the
:hostkey of the conn. You can set it directly. I’m not sure if there is another symptom at play here but that’s what I’ve done in the past (albeit in a toy app).LostKobrakai
This one might also be useful.
Schultzer
You might also set this in your routers scope with host Phoenix.Router — Phoenix v1.7.14
travisf
Thanks everyone! Indeed
hostseems the way to go. In my case there was a URL helper that was part of the redirect sending it to the root domain rather than the subdomain which I should have seen; just one of those small things that tends to get overlooked.