add keycloak
This commit is contained in:
parent
45ad9cb9d9
commit
411e1368d5
8 changed files with 251 additions and 13 deletions
|
@ -38,6 +38,11 @@ let
|
||||||
PHPFPMSiteConfig = callPackage ./php-fpm/siteconfig.nix {inherit utils;};
|
PHPFPMSiteConfig = callPackage ./php-fpm/siteconfig.nix {inherit utils;};
|
||||||
mkPHPFPMSiteConfig = callPackage ./php-fpm/mksiteconfig.nix {inherit PHPFPMSiteConfig;};
|
mkPHPFPMSiteConfig = callPackage ./php-fpm/mksiteconfig.nix {inherit PHPFPMSiteConfig;};
|
||||||
|
|
||||||
|
KeycloakConfig = callPackage ./keycloak/config.nix {inherit utils;};
|
||||||
|
mkKeycloakConfig = callPackage ./keycloak/mkconfig.nix {inherit KeycloakConfig;};
|
||||||
|
KeycloakService = callPackage ./keycloak/unit.nix {inherit utils;};
|
||||||
|
mkKeycloakService = callPackage ./keycloak/mkunit.nix {inherit KeycloakService;};
|
||||||
|
|
||||||
TtrssEnvironment = callPackage ./ttrss/environment.nix {};
|
TtrssEnvironment = callPackage ./ttrss/environment.nix {};
|
||||||
TtrssConfig = callPackage ./ttrss/config.nix {};
|
TtrssConfig = callPackage ./ttrss/config.nix {};
|
||||||
mkTtrssConfig = callPackage ./ttrss/mkconfig.nix {inherit TtrssConfig;};
|
mkTtrssConfig = callPackage ./ttrss/mkconfig.nix {inherit TtrssConfig;};
|
||||||
|
|
|
@ -5,7 +5,7 @@
|
||||||
}:
|
}:
|
||||||
{ configDir ? "/etc/haproxy"
|
{ configDir ? "/etc/haproxy"
|
||||||
, configFile ? "haproxy.cfg"
|
, configFile ? "haproxy.cfg"
|
||||||
, acls ? []
|
, frontends ? []
|
||||||
, backends ? []
|
, backends ? []
|
||||||
, certPath
|
, certPath
|
||||||
, user ? "haproxy"
|
, user ? "haproxy"
|
||||||
|
@ -37,7 +37,7 @@ let
|
||||||
(x: spaces + x + "\n")
|
(x: spaces + x + "\n")
|
||||||
(lib.strings.splitString "\n" content);
|
(lib.strings.splitString "\n" content);
|
||||||
|
|
||||||
acls_str = lib.strings.concatMapStrings (acl: indent " " acl) acls;
|
frontends_str = lib.strings.concatMapStrings (acl: indent " " acl) frontends;
|
||||||
backends_str = builtins.concatStringsSep "\n" backends;
|
backends_str = builtins.concatStringsSep "\n" backends;
|
||||||
|
|
||||||
in
|
in
|
||||||
|
@ -91,7 +91,7 @@ utils.mkConfigFile {
|
||||||
http-request add-header X-Forwarded-Proto https
|
http-request add-header X-Forwarded-Proto https
|
||||||
http-response set-header Strict-Transport-Security "max-age=15552000; includeSubDomains; preload;"
|
http-response set-header Strict-Transport-Security "max-age=15552000; includeSubDomains; preload;"
|
||||||
|
|
||||||
${acls_str}
|
${frontends_str}
|
||||||
|
|
||||||
${backends_str}
|
${backends_str}
|
||||||
'';
|
'';
|
||||||
|
|
|
@ -9,7 +9,7 @@
|
||||||
, statsPort ? null
|
, statsPort ? null
|
||||||
, prometheusStatsUri ? null
|
, prometheusStatsUri ? null
|
||||||
, certPath ? null
|
, certPath ? null
|
||||||
, acls ? []
|
, frontends ? []
|
||||||
, backends ? []
|
, backends ? []
|
||||||
, dependsOn ? {}
|
, dependsOn ? {}
|
||||||
}:
|
}:
|
||||||
|
@ -23,7 +23,7 @@
|
||||||
inherit prometheusStatsUri;
|
inherit prometheusStatsUri;
|
||||||
inherit certPath;
|
inherit certPath;
|
||||||
|
|
||||||
inherit acls backends;
|
inherit frontends backends;
|
||||||
};
|
};
|
||||||
|
|
||||||
inherit dependsOn;
|
inherit dependsOn;
|
||||||
|
|
|
@ -1,27 +1,41 @@
|
||||||
{ stdenv
|
{ stdenv
|
||||||
, pkgs
|
, pkgs
|
||||||
|
, lib
|
||||||
}:
|
}:
|
||||||
{ serviceName
|
{ serviceName
|
||||||
, serviceSocket
|
, serviceAddress ? null
|
||||||
|
, serviceSocket ? null
|
||||||
, phpFastcgi ? false
|
, phpFastcgi ? false
|
||||||
, phpDocroot ? null
|
, phpDocroot ? null
|
||||||
, phpIndex ? "index.php"
|
, phpIndex ? "index.php"
|
||||||
|
, extraUseBackendConditions ? {}
|
||||||
|
, extraFrontendOptions ? []
|
||||||
|
, extraBackendOptions ? []
|
||||||
}:
|
}:
|
||||||
|
|
||||||
|
assert lib.assertMsg (
|
||||||
|
(serviceAddress == null && serviceSocket != null)
|
||||||
|
|| (serviceAddress != null && serviceSocket == null)
|
||||||
|
) "set either serviceAddress or serviceSocket";
|
||||||
|
|
||||||
let
|
let
|
||||||
|
backendOptions = lib.concatMapStrings (x : "\n " + x) extraBackendOptions;
|
||||||
|
|
||||||
|
serviceBind = if serviceAddress != null then serviceAddress else serviceSocket;
|
||||||
|
|
||||||
backend =
|
backend =
|
||||||
if !phpFastcgi
|
if !phpFastcgi
|
||||||
then ''
|
then ''
|
||||||
backend ${serviceName}
|
backend ${serviceName}
|
||||||
mode http
|
mode http
|
||||||
option forwardfor
|
option forwardfor${backendOptions}
|
||||||
server ${serviceName}1 ${serviceSocket}
|
server ${serviceName}1 ${serviceBind}
|
||||||
'' else ''
|
'' else ''
|
||||||
backend ${serviceName}
|
backend ${serviceName}
|
||||||
mode http
|
mode http
|
||||||
option forwardfor
|
option forwardfor${backendOptions}
|
||||||
use-fcgi-app ${serviceName}-php-fpm
|
use-fcgi-app ${serviceName}-php-fpm
|
||||||
server ${serviceName}1 ${serviceSocket} proto fcgi
|
server ${serviceName}1 ${serviceBind} proto fcgi
|
||||||
|
|
||||||
fcgi-app ${serviceName}-php-fpm
|
fcgi-app ${serviceName}-php-fpm
|
||||||
log-stderr global
|
log-stderr global
|
||||||
|
@ -29,11 +43,18 @@ let
|
||||||
index ${phpIndex}
|
index ${phpIndex}
|
||||||
path-info ^(/.+\.php)(/.*)?$
|
path-info ^(/.+\.php)(/.*)?$
|
||||||
'';
|
'';
|
||||||
|
|
||||||
|
extraAclsCondition = lib.concatStrings (lib.attrsets.mapAttrsToList (k: v: "\nacl acl_${serviceName}_${k} ${v}") extraUseBackendConditions);
|
||||||
|
|
||||||
|
extraAclsOr = lib.concatStrings (lib.attrsets.mapAttrsToList (k: v: " OR acl_${serviceName}_${k}") extraUseBackendConditions);
|
||||||
in
|
in
|
||||||
{
|
{
|
||||||
acl = ''
|
frontend = ''
|
||||||
acl acl_${serviceName} hdr_beg(host) ${serviceName}.
|
acl acl_${serviceName} hdr_beg(host) ${serviceName}.${extraAclsCondition}
|
||||||
use_backend ${serviceName} if acl_${serviceName}
|
''
|
||||||
|
+ lib.concatMapStrings (x: x + "\n") extraFrontendOptions
|
||||||
|
+ ''
|
||||||
|
use_backend ${serviceName} if acl_${serviceName}${extraAclsOr}
|
||||||
'';
|
'';
|
||||||
|
|
||||||
inherit backend;
|
inherit backend;
|
||||||
|
|
62
keycloak/config.nix
Normal file
62
keycloak/config.nix
Normal file
|
@ -0,0 +1,62 @@
|
||||||
|
{ stdenv
|
||||||
|
, pkgs
|
||||||
|
, lib
|
||||||
|
, utils
|
||||||
|
}:
|
||||||
|
{ configDir ? "/etc/keycloak"
|
||||||
|
, configFile ? "keycloak.conf"
|
||||||
|
, logLevel ? "INFO"
|
||||||
|
, metricsEnabled ? false
|
||||||
|
, hostname ? "keycloak.hostname.com"
|
||||||
|
|
||||||
|
, dbType ? "postgres"
|
||||||
|
, dbUsername ? "keycloak"
|
||||||
|
, dbHost ? x: "localhost"
|
||||||
|
, dbPort ? "5432"
|
||||||
|
, dbDatabase ? "keycloak"
|
||||||
|
}:
|
||||||
|
{ KeycloakPostgresDB
|
||||||
|
}:
|
||||||
|
|
||||||
|
assert lib.assertOneOf "dbType" dbType ["postgres"];
|
||||||
|
|
||||||
|
utils.mkConfigFile {
|
||||||
|
name = configFile;
|
||||||
|
dir = configDir;
|
||||||
|
content = ''
|
||||||
|
# The password of the database user is given by an environment variable.
|
||||||
|
db=${dbType}
|
||||||
|
db-username=${dbUsername}
|
||||||
|
db-url-host=${dbHost {inherit KeycloakPostgresDB;}}
|
||||||
|
db-url-port=${dbPort}
|
||||||
|
db-url-database=${dbDatabase}
|
||||||
|
# db-url-properties= # Would be used for ssl, see https://github.com/NixOS/nixpkgs/blob/master/nixos/modules/services/web-apps/keycloak.nix#L491
|
||||||
|
|
||||||
|
# Observability
|
||||||
|
|
||||||
|
# If the server should expose metrics and healthcheck endpoints.
|
||||||
|
metrics-enabled=${if metricsEnabled then "true" else "false"}
|
||||||
|
|
||||||
|
# HTTP
|
||||||
|
|
||||||
|
# The file path to a server certificate or certificate chain in PEM format.
|
||||||
|
#https-certificate-file=''${kc.home.dir}conf/server.crt.pem
|
||||||
|
|
||||||
|
# The file path to a private key in PEM format.
|
||||||
|
#https-certificate-key-file=''${kc.home.dir}conf/server.key.pem
|
||||||
|
|
||||||
|
# The proxy address forwarding mode if the server is behind a reverse proxy.
|
||||||
|
# https://www.keycloak.org/server/reverseproxy
|
||||||
|
proxy=edge
|
||||||
|
|
||||||
|
# Do not attach route to cookies and rely on the session affinity capabilities from reverse proxy
|
||||||
|
#spi-sticky-session-encoder-infinispan-should-attach-route=false
|
||||||
|
|
||||||
|
# Hostname for the Keycloak server.
|
||||||
|
hostname=${hostname}
|
||||||
|
|
||||||
|
spi-x509cert-lookup-provider=haproxy
|
||||||
|
|
||||||
|
log-level=${logLevel}
|
||||||
|
'';
|
||||||
|
}
|
30
keycloak/mkconfig.nix
Normal file
30
keycloak/mkconfig.nix
Normal file
|
@ -0,0 +1,30 @@
|
||||||
|
{ KeycloakConfig
|
||||||
|
}:
|
||||||
|
{ name
|
||||||
|
, configDir ? "/etc/keycloak"
|
||||||
|
, configFile ? "keycloak.conf"
|
||||||
|
, logLevel ? "INFO"
|
||||||
|
, metricsEnabled ? false
|
||||||
|
, hostname ? "keycloak.hostname.com"
|
||||||
|
|
||||||
|
, dbType ? "postgres"
|
||||||
|
, dbUsername ? "keycloak"
|
||||||
|
, dbHost ? x: "localhost"
|
||||||
|
, dbPort ? "5432"
|
||||||
|
, dbDatabase ? "keycloak"
|
||||||
|
|
||||||
|
, dependsOn ? {}
|
||||||
|
}:
|
||||||
|
|
||||||
|
{
|
||||||
|
inherit name configDir configFile;
|
||||||
|
|
||||||
|
pkg = KeycloakConfig {
|
||||||
|
inherit configDir configFile hostname;
|
||||||
|
inherit logLevel metricsEnabled;
|
||||||
|
inherit dbType dbUsername dbHost dbPort dbDatabase;
|
||||||
|
};
|
||||||
|
|
||||||
|
inherit dependsOn;
|
||||||
|
type = "fileset";
|
||||||
|
}
|
26
keycloak/mkunit.nix
Normal file
26
keycloak/mkunit.nix
Normal file
|
@ -0,0 +1,26 @@
|
||||||
|
{ KeycloakService
|
||||||
|
}:
|
||||||
|
{ name
|
||||||
|
, configDir
|
||||||
|
, configFile
|
||||||
|
, user
|
||||||
|
, group
|
||||||
|
, dbPasswordFile
|
||||||
|
, postgresServiceName
|
||||||
|
, initialAdminFile ? null
|
||||||
|
|
||||||
|
, dependsOn ? {}
|
||||||
|
}:
|
||||||
|
{
|
||||||
|
inherit name configDir configFile;
|
||||||
|
|
||||||
|
pkg = KeycloakService {
|
||||||
|
inherit configDir configFile;
|
||||||
|
inherit user group;
|
||||||
|
inherit dbPasswordFile initialAdminFile;
|
||||||
|
inherit postgresServiceName;
|
||||||
|
};
|
||||||
|
|
||||||
|
inherit dependsOn;
|
||||||
|
type = "systemd-unit";
|
||||||
|
}
|
94
keycloak/unit.nix
Normal file
94
keycloak/unit.nix
Normal file
|
@ -0,0 +1,94 @@
|
||||||
|
{ stdenv
|
||||||
|
, pkgs
|
||||||
|
, lib
|
||||||
|
, utils
|
||||||
|
}:
|
||||||
|
{ configDir ? "/etc/keycloak"
|
||||||
|
, configFile ? "keycloak.conf"
|
||||||
|
, user ? "keycloak"
|
||||||
|
, group ? "keycloak"
|
||||||
|
, dbType ? "postgres"
|
||||||
|
, dbPasswordFile
|
||||||
|
, postgresServiceName
|
||||||
|
, initialAdminFile ? null
|
||||||
|
}:
|
||||||
|
{ ... }:
|
||||||
|
|
||||||
|
assert lib.assertOneOf "dbType" dbType ["postgres"];
|
||||||
|
|
||||||
|
let
|
||||||
|
keycloak = pkgs.keycloak.override {
|
||||||
|
# This is needed for keycloak to build with the correct driver.
|
||||||
|
confFile = pkgs.writeText "keycloak.conf" ''
|
||||||
|
db=${dbType}
|
||||||
|
'';
|
||||||
|
};
|
||||||
|
in
|
||||||
|
|
||||||
|
utils.systemd.mkService rec {
|
||||||
|
name = "keycloak";
|
||||||
|
|
||||||
|
content = ''
|
||||||
|
[Unit]
|
||||||
|
Description=Keycloak server
|
||||||
|
After=network-online.target
|
||||||
|
Wants=network-online.target systemd-networkd-wait-online.service ${postgresServiceName}
|
||||||
|
|
||||||
|
[Service]
|
||||||
|
User=${user}
|
||||||
|
Group=${group}
|
||||||
|
|
||||||
|
EnvironmentFile=${dbPasswordFile}
|
||||||
|
${if initialAdminFile != null then "EnvironmentFile="+initialAdminFile else ""}
|
||||||
|
Environment=PATH=${pkgs.coreutils}/bin
|
||||||
|
Environment=KC_HOME_DIR="/run/keycloak"
|
||||||
|
|
||||||
|
# running the ExecStartPre as root is not ideal, but at the moment
|
||||||
|
# the only solution for Quarkus modifying the serialized
|
||||||
|
# data under <keycloak-home>/lib/quarkus
|
||||||
|
# Raised upstream as https://github.com/keycloak/keycloak/discussions/10323
|
||||||
|
# ExecStartPre=!${keycloak}/bin/kc.sh -cf ${configDir}/${configFile} build
|
||||||
|
ExecStart=${keycloak}/bin/kc.sh -cf ${configDir}/${configFile} start
|
||||||
|
|
||||||
|
# ReadWritePaths=/var/lib/keycloak
|
||||||
|
# ReadWritePaths=/var/log/keycloak
|
||||||
|
# ReadWritePaths=/usr/share/java/keycloak/lib/quarkus
|
||||||
|
# ReadOnlyPaths=${configDir}
|
||||||
|
RuntimeDirectory=keycloak
|
||||||
|
DynamicUser=true
|
||||||
|
|
||||||
|
# Disable timeout logic and wait until process is stopped
|
||||||
|
TimeoutStopSec=0
|
||||||
|
TimeoutStartSec=10min
|
||||||
|
|
||||||
|
# SIGTERM signal is used to stop the Java process
|
||||||
|
KillSignal=SIGTERM
|
||||||
|
|
||||||
|
# Send the signal only to the JVM rather than its control group
|
||||||
|
KillMode=process
|
||||||
|
|
||||||
|
# Java process is never killed
|
||||||
|
SendSIGKILL=no
|
||||||
|
|
||||||
|
# When a JVM receives a SIGTERM signal it exits with code 143
|
||||||
|
SuccessExitStatus=143
|
||||||
|
|
||||||
|
# Hardening options
|
||||||
|
# CapabilityBoundingSet=
|
||||||
|
# AmbientCapabilities=CAP_NET_BIND_SERVICES
|
||||||
|
# NoNewPrivileges=true
|
||||||
|
# Fails with:
|
||||||
|
# Failed to set up mount namespacing: /run/systemd/unit-root/var/lib/keycloak: No such file or directory
|
||||||
|
# ProtectHome=true
|
||||||
|
# ProtectSystem=strict
|
||||||
|
# ProtectKernelTunables=true
|
||||||
|
# ProtectKernelModules=true
|
||||||
|
# ProtectControlGroups=true
|
||||||
|
# PrivateTmp=true
|
||||||
|
# PrivateDevices=true
|
||||||
|
# LockPersonality=true
|
||||||
|
|
||||||
|
[Install]
|
||||||
|
WantedBy=multi-user.target
|
||||||
|
'';
|
||||||
|
}
|
Loading…
Reference in a new issue