Authelia is an open-source authentication and authorization server that provides a single sign-on (SSO) solution for your applications. It supports various authentication methods, including LDAP, TOTP, and WebAuthn, and can be easily integrated with reverse proxies like Traefik to secure access to your applications.
Create the following directory structure for Authelia:
authelia/
├── authelia-cm.yml
├── authelia-db.yml
├── authelia-ingress.yml
├── authelia-middleware.yml
├── authelia-redis.yml
├── authelia-release.yml
├── authelia-repository.yml
├── authelia-secret.yml
├── authelia-users-secret.yml
└── authelia-users.yml
Add the following content to authelia/authelia-cm.yml:
---
apiVersion: v1
kind: ConfigMap
metadata:
name: authelia-config
namespace: tools
data:
configuration.yaml: |
server:
address: 'tcp4://:9091'
buffers:
read: 16384
log:
level: info
file_path: ''
keep_stdout: true
identity_validation:
elevated_session:
require_second_factor: true
reset_password:
jwt_lifespan: '5 minutes'
theme: dark
totp:
disable: false
issuer: 'example.com'
period: 30
skew: 1
algorithm: 'sha1'
digits: 6
secret_size: 32
allowed_algorithms:
- 'SHA1'
allowed_digits:
- 6
allowed_periods:
- 30
disable_reuse_security_policy: false
password_policy:
zxcvbn:
enabled: true
min_score: 4
authentication_backend:
file:
path: '/secrets/users.yml'
password:
algorithm: 'argon2'
argon2:
variant: 'argon2id'
iterations: 3
memory: 65535
parallelism: 4
key_length: 32
salt_length: 16
access_control:
default_policy: 'deny'
rules:
- domain: 'auth.example.com'
policy: bypass
- domain: 'invidious.example.com'
resources: '^/(api/v1|feed|videoplayback|vi/.+\.(jpg|webp)|ggpht|latest_version|sb)'
policy: bypass
- domain: 'immich.example.com'
policy: bypass
- domain: 'vw.example.com'
policy: bypass
- domain: '*.example.com'
policy: two_factor
session:
name: 'authelia_session'
cookies:
- domain: 'example.com'
authelia_url: 'https://auth.example.com'
redis:
host: 'authelia-dragonfly.tools.svc.cluster.local'
port: 6379
regulation:
max_retries: 4
find_time: 120
ban_time: 300
storage:
postgres:
address: 'tcp://authelia-db-cluster.tools.svc.cluster.local:5432'
database: authelia
username: authelia
tls:
skip_verify: true
server_name: ''
minimum_version: TLS1.2
notifier:
disable_startup_check: false
smtp:
address: submissions://smtp.gmail.com:465
username: [email protected]
sender: [email protected]
identifier: localhost
subject: "[Authelia] {title}"
startup_check_address: [email protected]
disable_require_tls: false
disable_html_emails: false
tls:
skip_verify: false
minimum_version: TLS1.2
ntp:
address: 'time.google.com:123'
version: 4
max_desync: '3s'
disable_startup_check: false
Add the following content to authelia/authelia-db.yml:
---
kind: "postgresql"
apiVersion: "acid.zalan.do/v1"
metadata:
name: "authelia-db-cluster"
namespace: "tools"
labels:
team: acid
spec:
teamId: "acid"
postgresql:
version: "17"
numberOfInstances: 2
volume:
size: "1Gi"
storageClass: "longhorn"
users:
authelia: []
databases:
authelia: authelia
Zalando Postgres Operator will deploy a PostgreSQL cluster for Authelia’s storage backend. It will create a secret named authelia.authelia-db-cluster.credentials.postgresql.acid.zalan.do in the tools namespace containing the database credentials. You need to copy the contents of this secret to a new secret named authelia-db-credentials that will be used by Authelia. You can’t refer to the original secret directly in the Authelia HelmRelease because of limitations in the Authelia Helm chart.
Add the following content to authelia/authelia-ingress.yml:
---
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: authelia
namespace: tools
annotations:
cert-manager.io/cluster-issuer: letsencrypt-cloudflare
spec:
ingressClassName: traefik
tls:
- hosts:
- auth.example.com
secretName: authelia-tls
rules:
- host: auth.example.com
http:
paths:
- path: /
pathType: Prefix
backend:
service:
name: authelia
port:
number: 9091
Add the following content to authelia/authelia-middleware.yml:
apiVersion: traefik.io/v1alpha1
kind: Middleware
metadata:
name: authelia
namespace: tools
spec:
forwardAuth:
address: http://authelia.tools.svc.cluster.local:9091/api/authz/forward-auth
trustForwardHeader: true
authResponseHeaders:
- Remote-User
- Remote-Groups
- Remote-Name
- Remote-Email
Add the following content to authelia/authelia-redis.yml:
---
apiVersion: dragonflydb.io/v1alpha1
kind: Dragonfly
metadata:
name: authelia-dragonfly
namespace: tools
spec:
replicas: 3
resources:
requests:
cpu: 100m
memory: 128Mi
limits:
cpu: 500m
memory: 512Mi
args:
- --maxmemory=256mb
Add the following content to authelia/authelia-release.yml:
---
apiVersion: helm.toolkit.fluxcd.io/v2
kind: HelmRelease
metadata:
name: authelia
namespace: tools
spec:
interval: 6h
chart:
spec:
chart: authelia
version: "0.11.4"
sourceRef:
kind: HelmRepository
name: authelia
namespace: flux-system
interval: 6h
install:
remediation:
retries: 3
upgrade:
remediation:
retries: 3
values:
configMap:
existingConfigMap: authelia-config
session:
redis:
enabled: true
host: authelia-dragonfly.tools.svc.cluster.local
port: 6379
password:
disabled: true
value: ''
storage:
postgres:
enabled: true
tls:
enabled: true
password:
disabled: true
secret_name: authelia-db-credentials
path: password
notifier:
smtp:
enabled: true
username: [email protected]
password:
secret_name: authelia-secrets
path: password
secret:
existingSecret: authelia-secrets
additionalSecrets:
authelia-secrets: {}
authelia-db-credentials: {}
service:
port: 9091
pod:
env:
- name: AUTHELIA_STORAGE_POSTGRES_PASSWORD_FILE
value: /secrets/authelia-db-credentials/password
initContainers:
- name: substitute-users-db
image: alpine
envFrom:
- secretRef:
name: authelia-users-secrets
command:
- sh
- -c
- |
apk add --no-cache gettext \
&& envsubst < /mnt/init/users.yml > /mnt/final/users.yml
volumeMounts:
- name: users-db-template
mountPath: /mnt/init/users.yml
subPath: users.yml
- name: users-db-final
mountPath: /mnt/final
extraVolumes:
- name: users-db-template
configMap:
name: authelia-users
- name: users-db-final
emptyDir: {}
extraVolumeMounts:
- name: users-db-final
mountPath: /secrets/users.yml
subPath: users.yml
Add the following content to authelia/authelia-repository.yml:
---
apiVersion: source.toolkit.fluxcd.io/v1
kind: HelmRepository
metadata:
name: authelia
namespace: flux-system
spec:
interval: 6h
url: https://charts.authelia.com
Add the following content to authelia/authelia-secret-tmp.yml:
---
apiVersion: v1
kind: Secret
metadata:
name: authelia-secrets
namespace: tools
type: Opaque
data:
identity_validation.reset_password.jwt.hmac.key: <base64-encoded-secret-key>
jwt.secret: <base64-encoded-secret-key>
notifier.smtp.username: <base64-encoded-email-username>
password: <base64-encoded-email-password>
session.authentication.key: <base64-encoded-secret-key>
session.encryption.key: <base64-encoded-secret-key>
storage.encryption.key: <base64-encoded-secret-key>
Encrypt the authelia/authelia-secret-tmp.yml file using Sealed-Secrets and save the output as authelia/authelia-secret.yml:
kubeseal --format yaml < authelia/authelia-secret-tmp.yml > authelia/authelia-secret.yml && \
rm authelia/authelia-secret-tmp.yml
Add the following content to authelia/authelia-users.yml:
---
apiVersion: v1
kind: ConfigMap
metadata:
name: authelia-users
namespace: tools
data:
users.yml: |
---
users:
admin_user:
displayname: 'Admin'
password: ${ADMIN}
email: '[email protected]'
groups:
- 'admin'
- 'dev'
# user_2:
# displayname: 'User 2'
# password: ${USER_2}
# email: '[email protected]'
# groups:
# - 'users'
Create a secret named authelia-users-secrets with user passwords:
---
apiVersion: v1
kind: Secret
metadata:
name: authelia-users-secrets
namespace: tools
type: Opaque
data:
ADMIN: <base64-encoded-admin-argon-hashed-password>
USER_2: <base64-encoded-user2-argon-hashed-password>
Encrypt the authelia-users-secrets secret using Sealed-Secrets:
kubeseal -o yaml < authelia-users-secrets.yml > authelia-users-secrets-sealed.yml && \
rm authelia-users-secrets.yml
Commit and push the changes to your git repo and wait for fluxcd to deploy Authelia.