titan-iac/services/jellyfin/deployment.yaml

153 lines
4.9 KiB
YAML

# services/jellyfin/deployment.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
name: jellyfin
namespace: jellyfin
labels:
app: jellyfin
spec:
replicas: 1
strategy:
type: RollingUpdate
rollingUpdate:
maxSurge: 0
maxUnavailable: 1
selector:
matchLabels:
app: jellyfin
template:
metadata:
labels:
app: jellyfin
spec:
# Clean up any lingering OIDC artifacts and strip the injected script tag
initContainers:
- name: strip-oidc
image: docker.io/jellyfin/jellyfin:10.11.5
securityContext:
runAsUser: 0
runAsGroup: 0
command:
- /bin/sh
- -c
- |
set -euxo pipefail
cp -a /jellyfin/jellyfin-web/. /web-root
# remove injected OIDC script tags everywhere just in case
for f in $(find /web-root -type f -name 'index.html'); do
sed -i '/oidc\/inject/d' "$f"
printf '%s\n' "$f"
done
# clean any lingering OIDC plugin artifacts on the config volume
rm -rf "/config/plugins/OIDC Authentication_"* /config/plugins/configurations/JellyfinOIDCPlugin.v2.xml || true
volumeMounts:
- name: web-root
mountPath: /web-root
- name: config
mountPath: /config
# Force all users to authenticate via the LDAP plugin provider by updating the DB on start.
# This keeps Flux enforcement for auth provider drift (e.g., after UI edits).
- name: set-ldap-auth-provider
image: docker.io/library/alpine:3.20
securityContext:
runAsUser: 0
runAsGroup: 0
command:
- /bin/sh
- -c
- |
set -euxo pipefail
apk add --no-cache sqlite
db="/config/data/jellyfin.db"
if [ -f "$db" ]; then
sqlite3 "$db" "UPDATE Users SET AuthenticationProviderId='Jellyfin.Plugin.LDAP_Auth.LdapAuthenticationProviderPlugin', Password=NULL, EnableLocalPassword=0 WHERE AuthenticationProviderId!='Jellyfin.Plugin.LDAP_Auth.LdapAuthenticationProviderPlugin';"
else
echo "db not found at $db, skipping"
fi
volumeMounts:
- name: config
mountPath: /config
nodeSelector:
jellyfin: "true"
securityContext:
runAsUser: 1000
fsGroup: 65532
fsGroupChangePolicy: OnRootMismatch
runAsGroup: 65532
runtimeClassName: nvidia
containers:
- name: jellyfin
image: docker.io/jellyfin/jellyfin:10.11.5
imagePullPolicy: IfNotPresent
ports:
- name: http
containerPort: 8096
env:
- name: NVIDIA_DRIVER_CAPABILITIES
value: "compute,video,utility"
- name: JELLYFIN_PublishedServerUrl
value: "https://stream.bstein.dev"
- name: PUID
value: "1000"
- name: PGID
value: "65532"
- name: UMASK
value: "002"
resources:
limits:
nvidia.com/gpu: 1
# cpu: "4"
# memory: 8Gi
requests:
nvidia.com/gpu: 1
cpu: "500m"
memory: 1Gi
volumeMounts:
- name: config
mountPath: /config
# Override LDAP plugin configuration from a secret to avoid embedding credentials in the PVC.
- name: ldap-config
mountPath: /config/plugins/configurations/LDAP-Auth.xml
subPath: ldap-config.xml
- name: cache
mountPath: /cache
- name: media
mountPath: /media
- name: web-root
mountPath: /jellyfin/jellyfin-web
lifecycle:
postStart:
exec:
command:
- /bin/sh
- -c
- |
set -eux
for f in $(find /jellyfin/jellyfin-web -type f -name 'index.html'); do
sed -i '/oidc\/inject/d' "$f" || true
done
securityContext:
runAsUser: 0
runAsGroup: 0
allowPrivilegeEscalation: false
readOnlyRootFilesystem: false
volumes:
- name: web-root
emptyDir: {}
- name: config
persistentVolumeClaim:
claimName: jellyfin-config-astreae
- name: cache
persistentVolumeClaim:
claimName: jellyfin-cache-astreae
- name: media
persistentVolumeClaim:
claimName: jellyfin-media-asteria-new
- name: ldap-config
secret:
secretName: jellyfin-ldap-config
items:
- key: ldap-config.xml
path: ldap-config.xml