Packages

phoenix_kit

1.7.227
1.7.227 1.7.226 1.7.225 1.7.224 1.7.223 1.7.222 1.7.221 1.7.220 1.7.219 1.7.218 1.7.217 1.7.216 1.7.215 1.7.214 1.7.213 1.7.212 1.7.211 1.7.210 1.7.209 1.7.208 1.7.207 1.7.206 1.7.205 1.7.204 1.7.203 1.7.202 1.7.201 1.7.200 1.7.199 1.7.198 1.7.197 1.7.196 1.7.194 1.7.193 1.7.192 1.7.191 1.7.190 1.7.189 1.7.187 1.7.186 1.7.185 1.7.184 1.7.183 1.7.182 1.7.181 1.7.180 1.7.179 1.7.178 1.7.177 1.7.176 1.7.175 1.7.174 1.7.173 1.7.172 1.7.171 1.7.170 1.7.169 1.7.168 1.7.167 1.7.166 1.7.165 1.7.164 1.7.162 1.7.161 1.7.160 1.7.159 1.7.157 1.7.156 1.7.155 1.7.154 1.7.153 1.7.152 1.7.151 1.7.150 1.7.149 1.7.146 1.7.145 1.7.144 1.7.143 1.7.138 1.7.133 1.7.132 1.7.131 1.7.130 1.7.128 1.7.126 1.7.125 1.7.121 1.7.120 1.7.119 1.7.118 1.7.117 1.7.116 1.7.115 1.7.114 1.7.113 1.7.112 1.7.111 1.7.110 1.7.109 1.7.108 1.7.107 1.7.106 1.7.105 1.7.104 1.7.103 1.7.102 1.7.101 1.7.100 1.7.99 1.7.98 1.7.97 1.7.96 1.7.95 1.7.94 1.7.93 1.7.92 1.7.91 1.7.90 1.7.89 1.7.88 1.7.87 1.7.86 1.7.85 1.7.84 1.7.83 1.7.82 1.7.81 1.7.80 1.7.79 1.7.78 1.7.77 1.7.76 1.7.75 1.7.74 1.7.71 1.7.70 1.7.69 1.7.66 1.7.65 1.7.64 1.7.63 1.7.62 1.7.61 1.7.59 1.7.58 1.7.57 1.7.56 1.7.55 1.7.54 1.7.53 1.7.52 1.7.51 1.7.49 1.7.44 1.7.43 1.7.42 1.7.41 1.7.39 1.7.38 1.7.37 1.7.36 1.7.34 1.7.33 1.7.31 1.7.30 1.7.29 1.7.28 1.7.27 1.7.26 1.7.25 1.7.24 1.7.23 1.7.22 1.7.21 1.7.20 1.7.19 1.7.18 1.7.17 1.7.16 1.7.15 1.7.14 1.7.13 1.7.12 1.7.11 1.7.10 1.7.9 1.7.8 1.7.7 1.7.6 1.7.5 1.7.4 1.7.3 1.7.2 1.7.1 1.7.0 1.6.20 1.6.19 1.6.18 1.6.17 1.6.16 1.6.15 1.6.14 1.6.13 1.6.12 1.6.11 1.6.10 1.6.9 1.6.8 1.6.7 1.6.6 1.6.5 1.6.4 1.6.3 1.5.2 1.5.1 1.5.0 1.4.9 1.4.8 1.4.7 1.4.6 1.4.5 1.4.4 1.4.3 1.4.2 1.4.1 1.4.0 1.3.2 1.3.1 1.3.0 1.2.10 1.2.9 1.2.8 1.2.7 1.2.5 1.2.4 1.2.2 1.2.1 1.2.0 1.1.0 1.0.0

A foundation for building Elixir Phoenix apps — SaaS, social networks, ERP systems, marketplaces, and more

Current section

Files

Jump to
phoenix_kit lib phoenix_kit.ex
Raw

lib/phoenix_kit.ex

defmodule PhoenixKit do
@moduledoc """
PhoenixKit
"""
alias PhoenixKit.Config
alias PhoenixKit.Users.Permissions
@doc """
Returns the current version of PhoenixKit.
## Examples
iex> PhoenixKit.version()
"1.3.3"
"""
@spec version() :: String.t()
def version do
Application.spec(:phoenix_kit, :vsn) |> to_string()
end
@doc """
Validates if PhoenixKit is properly configured.
Checks for required configuration keys and returns a status.
## Examples
iex> PhoenixKit.configured?()
false
"""
@spec configured?() :: boolean()
def configured? do
case Config.get(:repo, nil) do
nil -> false
_repo -> true
end
end
@doc """
Returns PhoenixKit configuration.
## Examples
iex> PhoenixKit.config()
%{ecto_repos: []}
"""
@spec config() :: map()
def config do
:phoenix_kit
|> Application.get_all_env()
|> Enum.into(%{})
end
@doc """
Final boot step — call from `Application.start/2` right after
`Supervisor.start_link/2`.
Picks up `:phoenix_kit_<x>` modules whose beams loaded after
`PhoenixKit.ModuleRegistry` initialised (a `:phoenix_kit_*` dep starts
*after* `:phoenix_kit` itself, so the registry's first scan can miss
it), then runs every registered module's `migrate_legacy/0` callback.
Returns the supervisor result unchanged so it composes:
def start(_type, _args) do
children = [...]
opts = [strategy: :one_for_one, name: MyApp.Supervisor]
Supervisor.start_link(children, opts) |> PhoenixKit.boot()
end
If `Supervisor.start_link/2` returned `{:error, _}`, this is a no-op —
the error passes through unchanged.
`mix phoenix_kit.install` and `mix phoenix_kit.update` wire this in
automatically; existing apps can add the call manually.
"""
@spec boot({:ok, pid()} | {:error, term()}) :: {:ok, pid()} | {:error, term()}
def boot({:ok, _pid} = result) do
PhoenixKit.ModuleRegistry.rescan()
PhoenixKit.ModuleRegistry.run_all_legacy_migrations()
register_custom_permission_keys()
result
end
def boot({:error, _reason} = result), do: result
# Custom permission keys declared in config:
#
# config :phoenix_kit,
# custom_permission_keys: [
# {"analytics", label: "Analytics"},
# "exports"
# ]
#
# `Permissions.register_custom_key/2` has to run AFTER boot, because the Admin
# auto-grant touches the database — which is why it could not simply be read
# from config at compile time, and why every host was writing an imperative
# call at the end of its own `Application.start/2`. Admin *tabs* have been
# declarative all along; permission keys were the odd one out.
#
# ⚠️ Two things a host needs to know:
#
# * This is only read from `boot/1`, which is opt-in. A host that never calls
# it registers nothing, silently. `install`/`update` wire the call in.
# * It is read once, at boot. Changing the config needs a restart.
#
# A key that already has an admin tab carrying `permission:` is registered by
# that tab and must NOT be listed here — double-registration hits the override
# path. This is for matrix-only keys with no tab of their own.
#
# Bad entries RAISE, failing app start. Config is a deploy-time contract, and
# logging-and-skipping would hide the mistake until a colleague hit a 403 —
# exactly the failure declaring keys is meant to prevent. (`Dashboard.Registry`
# rescues instead, correctly: one bad tab should not take the dashboard down.)
defp register_custom_permission_keys do
:phoenix_kit
|> Application.get_env(:custom_permission_keys, [])
|> Enum.each(fn
{key, opts} when is_binary(key) and is_list(opts) ->
Permissions.register_custom_key(key, opts)
key when is_binary(key) ->
Permissions.register_custom_key(key)
other ->
raise ArgumentError, """
Invalid entry in config :phoenix_kit, :custom_permission_keys — #{inspect(other)}
Each entry must be a key string, or a {key, opts} tuple:
custom_permission_keys: [
"exports",
{"analytics", label: "Analytics"}
]
"""
end)
end
end