Skip to content

Commit

Permalink
Update method documentation
Browse files Browse the repository at this point in the history
  • Loading branch information
danschultzer committed Aug 5, 2018
1 parent 125ba74 commit a3ec42b
Show file tree
Hide file tree
Showing 44 changed files with 557 additions and 83 deletions.
14 changes: 10 additions & 4 deletions lib/extensions/persistent_session/plug/cookie.ex
Original file line number Diff line number Diff line change
Expand Up @@ -39,8 +39,10 @@ defmodule PowPersistentSession.Plug.Cookie do
@ttl Integer.floor_div(:timer.hours(24) * 30, 1000)

@doc """
Sets a persistent session cookie with an auto generated token, and sets the
token as a key in the persistent session cache with the credentials.
Sets a persistent session cookie with an auto generated token.
The token is set as a key in the persistent session cache with
the user struct id.
"""
@spec create(Conn.t(), map(), Config.t()) :: Conn.t()
def create(conn, %{id: user_id}, config) do
Expand All @@ -55,8 +57,10 @@ defmodule PowPersistentSession.Plug.Cookie do
end

@doc """
If a persistent session cookie exists, it'll be expired, and the key in the
persistent session cache will be removed.
Expires the persistent session cookie.
If a persistent session cookie exists it'll be expired, and the token in
the persistent session cache will be deleted.
"""
@spec delete(Conn.t(), Config.t()) :: Conn.t()
def delete(conn, config) do
Expand All @@ -78,6 +82,8 @@ defmodule PowPersistentSession.Plug.Cookie do
end

@doc """
Authenticates a user with the persistent session cookie.
If a persistent session cookie exists, it'll fetch the credentials from the
persistent session cache, and create a new session and persistent session
cookie. The old persistent session cookie and session cache credentials will
Expand Down
15 changes: 15 additions & 0 deletions lib/mix/pow.ex
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,9 @@ defmodule Mix.Pow do
"""
alias Mix.Project

@doc """
Raises an exception if the project is an umbrella app.
"""
@spec no_umbrella!(binary()) :: :ok | no_return
def no_umbrella!(task) do
if Project.umbrella? do
Expand All @@ -13,6 +16,9 @@ defmodule Mix.Pow do
:ok
end

@doc """
Parses argument options into a map.
"""
@spec parse_options(OptionParser.argv(), Keyword.t(), Keyword.t()) :: map()
def parse_options(args, switches, default_opts) do
{opts, _parsed, _invalid} = OptionParser.parse(args, switches: switches)
Expand Down Expand Up @@ -42,6 +48,9 @@ defmodule Mix.Pow do
defp context_app_to_atom(config),
do: config

@doc """
Fetches context app for the project.
"""
@spec context_app :: atom() | no_return
def context_app do
this_app = otp_app()
Expand All @@ -62,6 +71,9 @@ defmodule Mix.Pow do
|> Keyword.fetch!(:app)
end

@doc """
Fetches the context base module for the app.
"""
@spec context_base(atom()) :: atom()
def context_base(app) do
case Application.get_env(app, :namespace, app) do
Expand All @@ -77,6 +89,9 @@ defmodule Mix.Pow do
end
end

@doc """
Fetches the library path for the context app.
"""
@spec context_lib_path(atom(), Path.t()) :: Path.t()
def context_lib_path(ctx_app, rel_path) do
context_app_path(ctx_app, Path.join(["lib", to_string(ctx_app), rel_path]))
Expand Down
3 changes: 3 additions & 0 deletions lib/mix/pow/ecto/migration.ex
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,9 @@ defmodule Mix.Pow.Ecto.Migration do
"""
alias Mix.{Ecto, Generator}

@doc """
Creates a migration file for the repo.
"""
@spec create_migration_files(atom(), binary(), binary()) :: any()
def create_migration_files(repo, name, content) do
base_name = "#{Macro.underscore(name)}.exs"
Expand Down
9 changes: 9 additions & 0 deletions lib/mix/pow/phoenix.ex
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,9 @@ defmodule Mix.Pow.Phoenix do
alias Mix.Generator
alias Mix.Pow

@doc """
Builds a map containing context and web module information.
"""
@spec parse_structure(map()) :: map()
def parse_structure(config) do
context_app = Map.get(config, :context_app, nil) || Pow.context_app()
Expand All @@ -29,6 +32,9 @@ defmodule Mix.Pow.Phoenix do
end
end

@doc """
Creates a view file for the web module.
"""
@spec create_view_file(atom(), binary(), atom(), binary()) :: :ok
def create_view_file(module, name, web_mod, web_prefix) do
path = Path.join([web_prefix, "views", Macro.underscore(module), "#{name}_view.ex"])
Expand All @@ -41,6 +47,9 @@ defmodule Mix.Pow.Phoenix do
Generator.create_file(path, content)
end

@doc """
Creates template files for the web module.
"""
@spec create_templates(atom(), binary(), binary(), [binary()]) :: :ok
def create_templates(module, name, web_prefix, actions) do
path = Path.join([web_prefix, "templates", Macro.underscore(module), name])
Expand Down
6 changes: 6 additions & 0 deletions lib/mix/pow/phoenix/mailer.ex
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,9 @@ defmodule Mix.Pow.Phoenix.Mailer do
"""
alias Mix.Generator

@doc """
Creates a mailer view file for the web module.
"""
@spec create_view_file(atom(), binary(), atom(), binary(), [binary()]) :: :ok
def create_view_file(module, name, web_mod, web_prefix, mails) do
subjects = subjects_methods(module, name, mails)
Expand All @@ -19,6 +22,9 @@ defmodule Mix.Pow.Phoenix.Mailer do
Generator.create_file(path, content)
end

@doc """
Creates mailer template files for the web module.
"""
@spec create_templates(atom(), binary(), binary(), [binary()]) :: :ok
def create_templates(module, name, web_prefix, mails) do
path = Path.join([web_prefix, "templates", Macro.underscore(module), name])
Expand Down
5 changes: 5 additions & 0 deletions lib/pow/application.ex
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,11 @@ defmodule Pow.Application do
@moduledoc false
use Application

@doc """
Starts the Pow application.
The EtsCache will be started by default.
"""
def start(_type, _args) do
import Supervisor.Spec

Expand Down
23 changes: 14 additions & 9 deletions lib/pow/config.ex
Original file line number Diff line number Diff line change
Expand Up @@ -7,21 +7,28 @@ defmodule Pow.Config do
defexception [:message]
end

@spec user_module(t()) :: atom()
def user_module(config) do
get(config, :user, nil) || raise_no_user_error()
end
@doc """
Gets the key value from the configuration.
If not found, it'll fallback to environment config, and lastly to the default
value.
"""
@spec get(t(), atom(), any()) :: any()
def get(config, key, default) do
Keyword.get(config, key, get_env_config(config, key, default))
end

@doc """
Puts a new key value to the configuration.
"""
@spec put(t(), atom(), any()) :: t()
def put(config, key, value) do
Keyword.put(config, key, value)
end

@doc """
Merges two configurations.
"""
@spec merge(t(), t()) :: t()
def merge(l_config, r_config) do
Keyword.merge(l_config, r_config)
Expand All @@ -40,11 +47,9 @@ defmodule Pow.Config do
end
end

@spec raise_no_user_error :: no_return
defp raise_no_user_error do
raise_error("No :user configuration option found for user schema module.")
end

@doc """
Raise a ConfigError exception.
"""
@spec raise_error(binary()) :: no_return
def raise_error(message) do
raise ConfigError, message: message
Expand Down
35 changes: 22 additions & 13 deletions lib/pow/ecto/context.ex
Original file line number Diff line number Diff line change
Expand Up @@ -85,8 +85,9 @@ defmodule Pow.Ecto.Context do

@doc """
Finds a user based on the user id, and verifies the password on the user.
User schema module and repo module will be fetched from the config. The
user id field is fetched from the user schema module.
User schema module and repo module will be fetched from the config. The user
id field is fetched from the user schema module.
"""
@spec authenticate(Config.t(), map()) :: user() | nil
def authenticate(config, params) do
Expand All @@ -110,8 +111,9 @@ defmodule Pow.Ecto.Context do
end

@doc """
Creates a new user. User schema module and repo module will be fetched from
config.
Creates a new user.
User schema module and repo module will be fetched from config.
"""
@spec create(Config.t(), map()) :: {:ok, user()} | {:error, Changeset.t()}
def create(config, params) do
Expand All @@ -123,8 +125,10 @@ defmodule Pow.Ecto.Context do
end

@doc """
Updates the user. User schema module will be fetched from provided user and
repo will be fetched from the config.
Updates the user.
User schema module will be fetched from provided user and repo will be
fetched from the config.
"""
@spec update(Config.t(), user(), map()) :: {:ok, user()} | {:error, Changeset.t()}
def update(config, user, params) do
Expand All @@ -134,16 +138,19 @@ defmodule Pow.Ecto.Context do
end

@doc """
Deletes the user. Repo module will be fetched from the config.
Deletes the user.
Repo module will be fetched from the config.
"""
@spec delete(Config.t(), user()) :: {:ok, user()} | {:error, Changeset.t()}
def delete(config, user) do
repo(config).delete(user)
end

@doc """
Retrieves an user by the provided clauses. User schema module and repo module
will be fetched from the config.
Retrieves an user by the provided clauses.
User schema module and repo module will be fetched from the config.
"""
@spec get_by(Config.t(), Keyword.t() | map()) :: user() | nil
def get_by(config, clauses) do
Expand All @@ -163,8 +170,9 @@ defmodule Pow.Ecto.Context do
end

@doc """
Inserts a changeset to the database. If succesful, the returned row will be
reloaded from the database.
Inserts a changeset to the database.
If succesful, the returned row will be reloaded from the database.
"""
@spec do_insert(Changeset.t(), Config.t()) :: {:ok, user()} | {:error, Changeset.t()}
def do_insert(changeset, config) do
Expand All @@ -174,8 +182,9 @@ defmodule Pow.Ecto.Context do
end

@doc """
Updates a changeset in the database. If succesful, the returned row will be
reloaded from the database.
Updates a changeset in the database.
If succesful, the returned row will be reloaded from the database.
"""
@spec do_update(Changeset.t(), Config.t()) :: {:ok, user()} | {:error, Changeset.t()}
def do_update(changeset, config) do
Expand Down
15 changes: 15 additions & 0 deletions lib/pow/ecto/schema.ex
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,13 @@ defmodule Pow.Ecto.Schema do
@moduledoc """
Handles the Ecto schema for user.
The macro will create a `:pow_fields` module attribute, and append fields
to it. The `pow_user_fields/0` macro will use these attributes to create
fields in the ecto schema.
A default `changeset/2` method is created, but can be overridden with a
custom `changeset/2` method.
## Usage
Configure `lib/my_project/users/user.ex` the following way:
Expand Down Expand Up @@ -63,6 +70,7 @@ defmodule Pow.Ecto.Schema do

@changeset_methods [:user_id_field_changeset, :password_changeset, :current_password_changeset]

@doc false
defmacro __pow_methods__ do
quoted_changeset_methods = for method <- @changeset_methods do
pow_method_name = String.to_atom("pow_#{method}")
Expand Down Expand Up @@ -111,6 +119,7 @@ defmodule Pow.Ecto.Schema do
end
end

@doc false
defmacro __register_fields__ do
quote do
Module.register_attribute(__MODULE__, :pow_fields, accumulate: true)
Expand All @@ -120,6 +129,7 @@ defmodule Pow.Ecto.Schema do
end
end

@doc false
defmacro __register_user_id_field__ do
quote do
@user_id_field unquote(__MODULE__).user_id_field(@pow_config)
Expand All @@ -136,6 +146,11 @@ defmodule Pow.Ecto.Schema do
def user_id_field(map) when is_map(map), do: user_id_field(map.__struct__)
def user_id_field(module), do: module.pow_user_id_field()

@doc """
Normalizes the user id field.
Keeps the user id field value case insensitive.
"""
@spec normalize_user_id_field_value(binary()) :: binary()
def normalize_user_id_field_value(value), do: String.downcase(value)
end
31 changes: 31 additions & 0 deletions lib/pow/ecto/schema/changeset.ex
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,13 @@ defmodule Pow.Ecto.Schema.Changeset do
@password_min_length 10
@password_max_length 4096

@doc """
Validates the user id field.
The user id field is always required. It will be treated as case insensitive,
and it's required to be unique. If the user id field is `:email`, the value
will be validated as an e-mail address too.
"""
@spec user_id_field_changeset(Ecto.Schema.t() | Changeset.t(), map(), Config.t()) :: Changeset.t()
def user_id_field_changeset(user_or_changeset, params, _config) do
user_id_field = Schema.user_id_field(user_or_changeset)
Expand All @@ -36,6 +43,18 @@ defmodule Pow.Ecto.Schema.Changeset do
|> Changeset.unique_constraint(user_id_field)
end

@doc """
Validates the password field.
The `password` and `confirm_password` params is required to be equal. A
password hash is generated by using `:password_hash_methods` in the
configuration. The password is always required if the password hash is nil,
and it's required to be between `:password_min_length` to
`:password_max_length` characters long.
The password hash is only generated if the changeset is valid, but always
required.
"""
@spec password_changeset(Ecto.Schema.t() | Changeset.t(), map(), Config.t()) :: Changeset.t()
def password_changeset(user_or_changeset, params, config) do
user_or_changeset
Expand All @@ -47,6 +66,12 @@ defmodule Pow.Ecto.Schema.Changeset do
|> Changeset.validate_required([:password_hash])
end

@doc """
Validates the current password field.
It's only required to provide a current password if the `password_hash`
value exists in the data struct.
"""
@spec current_password_changeset(Ecto.Schema.t() | Changeset.t(), map(), Config.t()) :: Changeset.t()
def current_password_changeset(user_or_changeset, params, config) do
user_or_changeset
Expand Down Expand Up @@ -79,6 +104,12 @@ defmodule Pow.Ecto.Schema.Changeset do
end
end

@doc """
Verifies a password in a struct.
The password will be verified by using the `:password_hash_methods` in the
configuration.
"""
@spec verify_password(Ecto.Schema.t(), binary(), Config.t()) :: boolean()
def verify_password(%{password_hash: password_hash}, password, config) do
config
Expand Down
Loading

0 comments on commit a3ec42b

Please sign in to comment.