Git Product home page Git Product logo

phoenix_token_auth's Introduction

PhoenixTokenAuth

Adds token authentication to Phoenix apps using Ecto.

An example app is available at https://github.com/manukall/phoenix_token_auth_react.

Setup

You need to have a user model with at least the following schema:

defmodule MyApp.User do
  use Ecto.Model

  schema "users" do
    field  :email,                       :string
    field  :hashed_password,             :string
    field  :hashed_confirmation_token,   :string
    field  :confirmed_at,                Ecto.DateTime
    field  :hashed_password_reset_token, :string
  end
end

Then add PhoenixTokenAuth to your Phoenix router:

defmodule MyApp.Router do
  use Phoenix.Router
  require PhoenixTokenAuth

  pipeline :authenticated do
    plug PhoenixTokenAuth.Plug
  end

  scope "/api" do
    pipe_through :api

    PhoenixTokenAuth.mount
  end

  scope "/api" do
    pipe_through :authenticated
    pipe_through :api

    resources: messages, MessagesController
  end
end

This generates routes for sign-up and login and protects the messages resources from unauthenticated access.

The generated routes are:

method path description
POST /api/users sign up
POST /api/users/:id/confirm confirm account
POST /api/session login, will return a token as JSON
POST /api/password_resets request a reset-password-email
POST /api/password_resets/reset reset a password

Inside the controller, the authenticated user's id is accessible inside the connections assigns:

def index(conn, _params) do
  user_id = conn.assigns.authenticated_user.id
  ...
end

Now add configuration:

# config/config.exs
config :phoenix_token_auth,
  user_model: Myapp.User,                                                    # ecto model used for authentication
  repo: Myapp.Repo,                                                          # ecto repo
  crypto_provider: Comeonin.Bcrypt,                                          # crypto provider for hashing passwords/tokens. see http://hexdocs.pm/comeonin/
  token_secret: "the_very_secret_token",                                     # secret string used to sign the authentication token
  token_validity_in_minutes: 7 * 24 * 60                                     # minutes from login until a token expires
  email_sender: "[email protected]",                                         # sender address of emails sent by the app
  welcome_email_subject: fn user -> "Hello #{user.email}" end,               # function returning the subject of a welcome email
  welcome_email_body: fn user, confirmation_token -> confirmation_token end, # function returning the body of a welcome email
  password_reset_email_subject: fn user -> "Hello #{user.email}" end,        # function returning the subject of a welcome email
  password_reset_email_body: fn user, reset_token -> reset_token end,        # function returning the body of a welcome email
  mailgun_domain: "example.com"                                              # domain of your mailgun account
  mailgun_key: "secret"                                                      # secret key of your mailgun account

Usage

Signing up / Registering a new user

  • POST request to /api/users.
  • Body should be JSON encoded {user: {email: "[email protected]", password: "secret"}}.
  • This will send an email containing the confirmation token.

Confirming a user

  • POST request to /api/users/:id/confirm
  • Body should be JSON encoded {confirmation_token: "token form the email"}
  • This will mark the user as confirmed and return an authentication token as JSON: {token: "the_token"}.

Logging in

  • POST request to /api/sessions
  • Body should be JSON encoded {email: "[email protected]", password: "secret"}
  • Will return an authentication token as JSON: {token: "the_token"}

Requesting a protected resource

  • Add a header with key Authorization and value Bearer #{token} to the request.
  • #{token} is the token from either account confirmation or logging in.

Logging out

  • Logging out is completely client side. Just stop sending the Authorization header.

Resetting password

  • POST request to /api/password_resets
  • Body should be JSON encoded {email: "[email protected]"}
  • This will send an email as configured.
  • Once the reset token is received in the email, make a POST request to /api/password_resets/reset with body {user_id: 123, password_reset_token: "the_token_from_the_email", password: "the_new_password"}
  • This will change the users password and return an authentication token as JSON: {token: "the_token"}.

TODO:

  • Better documentation
  • Validations of email and password (format, length, ...)

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo 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.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.