Comments (11)
Perfect! I'll try that later today or tomorrow.
As mentioned I'll try to make a PR for the guides to cover this part.
The invitation extension could be great but I never used this approach before.
In our main saas app this is what happens: client request -> admin setup an account with the first user -> client can add the other users of his team. So basically every step is protected (need to be logged). That's what I'm trying to do as an exercise for pow. What is interesting here is that we need few different changesets and render actions depending on who calls the action.
I like the fact that extracting Pow.Plug is quite easy.
Authentication is just a series of Plug (encrypt pass, check pass, validate token, ....), it seems that Pow allow this approach (Pow is just an engine exposing plugs as an interface).
I'll close this once the experience is finished and the guide completed ;)
from pow.
Ok, perfect.
I think that I have all the information to finish the guide.
I'll PR soon.
Thanks!
from pow.
I've been working on a guide for invitation/closed registration setup myself, and I think I'll create an extension for it. There's been a lot of interest for invitation setup, and it's probably not trivial for people to implement.
From the top of my head this is what you would need:
- Add a hidden input box with the invitation token value to the registration form
- Add changeset validation for invitation token
And for most cases you would also need:
- Create a custom controller for handling invitation registrations
- Create a plug action to validate invitation tokens
This is the basis of dynamic invitation registrations. I'll see if I can build the base for an invitation extension soon. It would make it a lot easier.
As for the custom registration controller, I would set keep it simple like this:
defmodule MyAppWeb.RegistrationController do
use MyAppWeb, :controller
alias Pow.Phoenix.RegistrationController, as: PowRegistrationController
def new(conn, params), do: PowRegistrationController.new(conn, params)
def create(conn, params), do: PowRegistrationController.create(conn, params)
def edit(conn, params), do: PowRegistrationController.edit(conn, params)
def update(conn, params), do: PowRegistrationController.update(conn, params)
def delete(conn, params), do: PowRegistrationController.delete(conn, params)
end
Later, if necessary, it can be expanded by extracting the actual plug actions:
def new(conn, _params) do
changeset = Pow.Plug.change_user(conn)
conn
|> assign(:changeset, changeset)
|> render("new.html")
end
Remember that the views and templates has to be renamed, and moved. You would need to make your own routes too instead of using pow_routes
.
Nobody have made custom registration controllers before so there's probably a bunch of caveats that I haven't thought about, and there may be things in pow that should be changed to make it easier to work with.
If you're willing to try it out, please let me know about your experience as the option for this kind of customization is a vital part of Pow 😄
from pow.
I'm working on the session part and I can't login.
Considering this code:
# Session controller
use PowtestWeb, :controller
def new(conn, _params) do
changeset = Pow.Plug.change_user(conn)
conn
|> render("login.html", changeset: changeset)
end
def create(conn, params) do
case Pow.Plug.authenticate_user(conn, params) do
{:ok, conn} ->
conn
|> put_flash(:info, "Welcome back")
|> redirect(to: Routes.page_path(conn, :private_page))
{:error, conn} ->
conn
|> put_flash(:info, "Email or Password incorect")
|> render( "login.html", changeset: conn.assign.changeset )
end
end
# Routes
scope "/", PowtestWeb do
pipe_through :browser
get "/", PageController, :index
get "/signup", AuthController, :new
post "/signup", AuthController, :create, as: :signup
get "/login", SessionsController, :new, as: :login
post "/login", SessionsController, :create, as: :login
delete "/logout", SessionsController, :delete, as: :logout
end
When trying to log, I've got this error: no function clause matching in String.downcase/2
nil
seems to have been passed to the function, but the params got the right informations.
Any Idea why?
from pow.
I think this may be what's missing (the Pow.Plug.authenticate_user/2
expects a map with email
and password
):
def create(conn, %{"user" => user_params}) do
case Pow.Plug.authenticate_user(conn, user_params) do
# ...
end
end
from pow.
Actually that was my initial approach but when doing this I've got:
KeyError at POST /login key :assign not found in
Reading the pow code I see that the pattern match occurs later and the function need the full params, but I'm maybe wrong.
from pow.
I think this bit is the problem:
|> render( "login.html", changeset: conn.assign.changeset )
It should be:
|> render( "login.html", changeset: conn.assigns.changeset )
from pow.
Thanks for the typo. But it didn't solve the error:
key :changeset not found in: %{current_user: nil}
I'm actually checking what Pow.Plug.authenticate_user
is actually returning in case of an error.
edit: the login works if a legit user try the form.
from pow.
Yeah, there's no changeset automatically assigned in that call. You'll need to do this instead:
def create(conn, %{"user" => user_params}) do
case Pow.Plug.authenticate_user(conn, user_params) do
{:ok, conn} ->
conn
|> put_flash(:info, "Welcome back")
|> redirect(to: Routes.page_path(conn, :private_page))
{:error, conn} ->
changeset = Pow.Plug.change_user(conn, conn.params["user"])
conn
|> put_flash(:info, "Email or Password incorect")
|> render( "login.html", changeset: changeset)
end
end
Here's the doc/specs: https://github.com/danschultzer/pow/blob/master/lib/pow/plug.ex#L72-L77
The plug actions will mostly just transform conn, and in authenticate_user
it'll do nothing if an error occurs.
from pow.
Also, this is the controller action in Pow: https://github.com/danschultzer/pow/blob/master/lib/pow/phoenix/controllers/session_controller.ex#L32-L50
Pow has the action split into process_ACTION
and response_ACTION
, but should be easy to read since it usually only consists of one plug method call, and then just processing the results of that call.
from pow.
I just PR for the new guide. I'll keep improving it.
Maybe a ref to it in the installation guide could help?
from pow.
Related Issues (20)
- Replacing Phoenix.Token with JWT-based for signing and verifiying of tokens HOT 1
- Unable to logout user in Pow API HOT 2
- Feature Request: Apple Passkeys HOT 1
- Pow.Plug.authenticate_user/1 performance HOT 2
- Reset password - test fails issue HOT 1
- Upgrading to Phoenix 1.7 HOT 5
- Create account without email/password using some unique ID?
- Phoenix 1.7 compilers warning HOT 1
- Maintain case when storing emails HOT 2
- Permissions issues with mnesia backend for Pow HOT 15
- Improve mix tasks
- Crash @missing_field? in Schema.ex HOT 1
- Inject values on registration HOT 2
- users_context seems to be ignored HOT 1
- Upgrading POW from 1.6 to 1.7 HOT 12
- Changeset errors into view HOT 1
- POW & LiveView - best way to implement `assigns.current_user` ? HOT 7
- Elixir 1.15 deprecation warnings HOT 1
- Persistence of stale session ids in MnesiaCache HOT 10
- Phoenix 1.6 App upgraded to 1.7 warning about layout conflicts. HOT 2
Recommend Projects
-
React
A declarative, efficient, and flexible JavaScript library for building user interfaces.
-
Vue.js
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
-
Typescript
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
-
TensorFlow
An Open Source Machine Learning Framework for Everyone
-
Django
The Web framework for perfectionists with deadlines.
-
Laravel
A PHP framework for web artisans
-
D3
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
-
Recommend Topics
-
javascript
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
-
web
Some thing interesting about web. New door for the world.
-
server
A server is a program made to process requests and deliver data to clients.
-
Machine learning
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
-
Visualization
Some thing interesting about visualization, use data art
-
Game
Some thing interesting about game, make everyone happy.
Recommend Org
-
Facebook
We are working to build community through open source technology. NB: members must have two-factor auth.
-
Microsoft
Open source projects and samples from Microsoft.
-
Google
Google ❤️ Open Source for everyone.
-
Alibaba
Alibaba Open Source for everyone
-
D3
Data-Driven Documents codes.
-
Tencent
China tencent open source team.
from pow.