feat: add smtp settings
All checks were successful
continuous-integration/drone/push Build is passing

This commit is contained in:
Simon 2026-03-12 13:39:48 +01:00
parent c4135308e6
commit a4f3aa5d6f
Signed by: simon
GPG key ID: 40E7A58C4AA1EDB2
23 changed files with 2424 additions and 152 deletions

View file

@ -58,7 +58,8 @@ defmodule Mv.Membership.Setting do
"""
use Ash.Resource,
domain: Mv.Membership,
data_layer: AshPostgres.DataLayer
data_layer: AshPostgres.DataLayer,
primary_read_warning?: false
# Used in join_form_field_ids validation (compile-time to avoid recompiling regex and list on every validation)
@uuid_pattern ~r/^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$/i
@ -73,8 +74,50 @@ defmodule Mv.Membership.Setting do
description "Global application settings (singleton resource)"
end
# All public attributes except smtp_password, used to exclude it from default reads.
# This list is used in the read prepare to prevent the sensitive password from being
# returned in standard reads (it can still be read via explicit select in Config).
@public_attributes [
:id,
:club_name,
:member_field_visibility,
:member_field_required,
:include_joining_cycle,
:default_membership_fee_type_id,
:vereinfacht_api_url,
:vereinfacht_api_key,
:vereinfacht_club_id,
:vereinfacht_app_url,
:oidc_client_id,
:oidc_base_url,
:oidc_redirect_uri,
:oidc_client_secret,
:oidc_admin_group_name,
:oidc_groups_claim,
:oidc_only,
:smtp_host,
:smtp_port,
:smtp_username,
:smtp_ssl,
:smtp_from_name,
:smtp_from_email,
:join_form_enabled,
:join_form_field_ids,
:join_form_field_required,
:inserted_at,
:updated_at
]
actions do
defaults [:read]
read :read do
primary? true
# smtp_password is excluded from the default select to prevent it from being returned
# in plaintext via standard reads. Config reads it via an explicit select internally.
prepare fn query, _context ->
Ash.Query.select(query, @public_attributes)
end
end
# Internal create action - not exposed via code interface
# Used only as fallback in get_settings/0 if settings don't exist
@ -97,6 +140,13 @@ defmodule Mv.Membership.Setting do
:oidc_admin_group_name,
:oidc_groups_claim,
:oidc_only,
:smtp_host,
:smtp_port,
:smtp_username,
:smtp_password,
:smtp_ssl,
:smtp_from_name,
:smtp_from_email,
:join_form_enabled,
:join_form_field_ids,
:join_form_field_required
@ -126,6 +176,13 @@ defmodule Mv.Membership.Setting do
:oidc_admin_group_name,
:oidc_groups_claim,
:oidc_only,
:smtp_host,
:smtp_port,
:smtp_username,
:smtp_password,
:smtp_ssl,
:smtp_from_name,
:smtp_from_email,
:join_form_enabled,
:join_form_field_ids,
:join_form_field_required
@ -429,6 +486,52 @@ defmodule Mv.Membership.Setting do
description "When true and OIDC is configured, sign-in shows only OIDC (password login hidden)"
end
# SMTP configuration (can be overridden by ENV)
attribute :smtp_host, :string do
allow_nil? true
public? true
description "SMTP server hostname (e.g. smtp.example.com)"
end
attribute :smtp_port, :integer do
allow_nil? true
public? true
description "SMTP server port (e.g. 587 for TLS, 465 for SSL, 25 for plain)"
end
attribute :smtp_username, :string do
allow_nil? true
public? true
description "SMTP authentication username"
end
attribute :smtp_password, :string do
allow_nil? true
public? false
description "SMTP authentication password (sensitive)"
sensitive? true
end
attribute :smtp_ssl, :string do
allow_nil? true
public? true
description "SMTP TLS/SSL mode: 'tls', 'ssl', or 'none'"
end
attribute :smtp_from_name, :string do
allow_nil? true
public? true
description "Display name for the transactional email sender (e.g. 'Mila'). Overrides MAIL_FROM_NAME env."
end
attribute :smtp_from_email, :string do
allow_nil? true
public? true
description "Email address for the transactional email sender. Must be owned by the SMTP user. Overrides MAIL_FROM_EMAIL env."
end
# Join form (Beitrittsformular) settings
attribute :join_form_enabled, :boolean do
allow_nil? false