phase0: add app skeleton, config cache, and precommit alias

This commit is contained in:
2026-03-13 18:56:23 +01:00
parent cc78558612
commit 5e478cd305
18 changed files with 281 additions and 5 deletions

View File

@@ -0,0 +1,22 @@
defmodule Parrhesia.Application do
@moduledoc false
use Application
@impl true
def start(_type, _args) do
children = [
Parrhesia.Telemetry,
Parrhesia.Config,
Parrhesia.Storage.Supervisor,
Parrhesia.Subscriptions.Supervisor,
Parrhesia.Auth.Supervisor,
Parrhesia.Policy.Supervisor,
Parrhesia.Web.Endpoint,
Parrhesia.Tasks.Supervisor
]
opts = [strategy: :one_for_one, name: Parrhesia.Supervisor]
Supervisor.start_link(children, opts)
end
end

View File

@@ -0,0 +1,16 @@
defmodule Parrhesia.Auth.Supervisor do
@moduledoc """
Supervision entrypoint for AUTH challenge/session tracking.
"""
use Supervisor
def start_link(init_arg \\ []) do
Supervisor.start_link(__MODULE__, init_arg, name: __MODULE__)
end
@impl true
def init(_init_arg) do
Supervisor.init([], strategy: :one_for_one)
end
end

65
lib/parrhesia/config.ex Normal file
View File

@@ -0,0 +1,65 @@
defmodule Parrhesia.Config do
@moduledoc """
Runtime configuration cache backed by ETS.
"""
use GenServer
@table __MODULE__
@root_key :config
def start_link(init_arg \\ []) do
GenServer.start_link(__MODULE__, init_arg, name: __MODULE__)
end
@impl true
def init(_init_arg) do
_table = :ets.new(@table, [:named_table, :public, read_concurrency: true])
config =
:parrhesia
|> Application.get_all_env()
|> Enum.into(%{})
:ets.insert(@table, {@root_key, config})
{:ok, %{}}
end
@spec all() :: map() | keyword()
def all do
case :ets.lookup(@table, @root_key) do
[{@root_key, config}] -> config
[] -> %{}
end
end
@spec get([atom()], term()) :: term()
def get(path, default \\ nil) when is_list(path) do
case fetch(path) do
{:ok, value} -> value
:error -> default
end
end
defp fetch(path) do
Enum.reduce_while(path, {:ok, all()}, fn key, {:ok, current} ->
case fetch_key(current, key) do
{:ok, value} -> {:cont, {:ok, value}}
:error -> {:halt, :error}
end
end)
end
defp fetch_key(current, key) when is_map(current), do: Map.fetch(current, key)
defp fetch_key(current, key) when is_list(current) do
if Keyword.keyword?(current) do
Keyword.fetch(current, key)
else
:error
end
end
defp fetch_key(_current, _key), do: :error
end

View File

@@ -0,0 +1,16 @@
defmodule Parrhesia.Policy.Supervisor do
@moduledoc """
Supervision entrypoint for policy/rate-limit/ACL workers.
"""
use Supervisor
def start_link(init_arg \\ []) do
Supervisor.start_link(__MODULE__, init_arg, name: __MODULE__)
end
@impl true
def init(_init_arg) do
Supervisor.init([], strategy: :one_for_one)
end
end

View File

@@ -0,0 +1,16 @@
defmodule Parrhesia.Storage.Supervisor do
@moduledoc """
Supervision entrypoint for storage adapter processes.
"""
use Supervisor
def start_link(init_arg \\ []) do
Supervisor.start_link(__MODULE__, init_arg, name: __MODULE__)
end
@impl true
def init(_init_arg) do
Supervisor.init([], strategy: :one_for_one)
end
end

View File

@@ -0,0 +1,16 @@
defmodule Parrhesia.Subscriptions.Supervisor do
@moduledoc """
Supervision entrypoint for subscription index and fanout workers.
"""
use Supervisor
def start_link(init_arg \\ []) do
Supervisor.start_link(__MODULE__, init_arg, name: __MODULE__)
end
@impl true
def init(_init_arg) do
Supervisor.init([], strategy: :one_for_one)
end
end

View File

@@ -0,0 +1,16 @@
defmodule Parrhesia.Tasks.Supervisor do
@moduledoc """
Supervision entrypoint for background maintenance jobs.
"""
use Supervisor
def start_link(init_arg \\ []) do
Supervisor.start_link(__MODULE__, init_arg, name: __MODULE__)
end
@impl true
def init(_init_arg) do
Supervisor.init([], strategy: :one_for_one)
end
end

View File

@@ -0,0 +1,16 @@
defmodule Parrhesia.Telemetry do
@moduledoc """
Supervision entrypoint for relay telemetry workers.
"""
use Supervisor
def start_link(init_arg \\ []) do
Supervisor.start_link(__MODULE__, init_arg, name: __MODULE__)
end
@impl true
def init(_init_arg) do
Supervisor.init([], strategy: :one_for_one)
end
end

View File

@@ -0,0 +1,16 @@
defmodule Parrhesia.Web.Endpoint do
@moduledoc """
Supervision entrypoint for WS/HTTP ingress.
"""
use Supervisor
def start_link(init_arg \\ []) do
Supervisor.start_link(__MODULE__, init_arg, name: __MODULE__)
end
@impl true
def init(_init_arg) do
Supervisor.init([], strategy: :one_for_one)
end
end