132 lines
3.7 KiB
Nix
132 lines
3.7 KiB
Nix
{
|
|
config,
|
|
lib,
|
|
...
|
|
}: let
|
|
cfg = config.hive.gotify-instance;
|
|
server-config = {
|
|
server = {
|
|
listenaddr = "localhost";
|
|
port = 54545;
|
|
ssl.enabled = false;
|
|
ssl.redirecttohttps = false;
|
|
cors.alloworigins = ["${cfg.instanceFQDN}"];
|
|
stream.allowedorigins = ["${cfg.instanceFQDN}"];
|
|
};
|
|
database = {
|
|
dialect = "postgres";
|
|
connection = "host=/run/postgresql dbname=${cfg.user} user=${cfg.user}";
|
|
};
|
|
defaultuser = {
|
|
name = "admin";
|
|
pass = config.sops.placeholder.${cfg.adminPasswordSopsKey};
|
|
};
|
|
registration = false;
|
|
};
|
|
server-config-yaml = lib.generators.toYAML {} server-config;
|
|
in {
|
|
options.hive.gotify-instance = {
|
|
enable = lib.mkEnableOption "Enable the Gotify instance";
|
|
instanceFQDN = lib.mkOption {
|
|
type = lib.types.singleLineStr;
|
|
example = "gotify.example.com";
|
|
description = "Fully qualified domain name of the Gotify instance";
|
|
};
|
|
user = lib.mkOption {
|
|
type = lib.types.singleLineStr;
|
|
default = "gotify";
|
|
description = "The user to run the service as";
|
|
};
|
|
group = lib.mkOption {
|
|
type = lib.types.singleLineStr;
|
|
default = "gotify";
|
|
description = "The group to run the service as";
|
|
};
|
|
adminPasswordSopsKey = lib.mkOption {
|
|
type = lib.types.singleLineStr;
|
|
description = "The SOPS key for the default admin user";
|
|
};
|
|
};
|
|
|
|
config = lib.mkIf cfg.enable {
|
|
services.gotify.enable = true;
|
|
|
|
# Config setup
|
|
sops.templates."gotify-server-config.yml" = {
|
|
owner = cfg.user;
|
|
content = server-config-yaml;
|
|
};
|
|
environment.etc."gotify/config.yml".source = config.sops.templates."gotify-server-config.yml".path;
|
|
|
|
# User setup
|
|
users.users = lib.mkIf (cfg.user == "gotify") {
|
|
gotify = {
|
|
description = "Gotify service";
|
|
useDefaultShell = true;
|
|
group = cfg.group;
|
|
isSystemUser = true;
|
|
};
|
|
};
|
|
|
|
users.groups = lib.mkIf (cfg.group == "gotify") {
|
|
gotify = {};
|
|
};
|
|
|
|
# Configure gotify to run as the specified user (for postgres authentication)
|
|
systemd.services.gotify-server = {
|
|
serviceConfig = {
|
|
DynamicUser = lib.mkForce false;
|
|
User = cfg.user;
|
|
RuntimeDirectory = "gotify";
|
|
};
|
|
};
|
|
|
|
# Fallback server with only 403
|
|
services.nginx.virtualHosts.${config.networking.domain} = lib.mkDefault {
|
|
default = true;
|
|
locations."/".return = 403;
|
|
forceSSL = true;
|
|
enableACME = true;
|
|
};
|
|
|
|
# Virtual host for gotify
|
|
services.nginx.virtualHosts."${cfg.instanceFQDN}" = {
|
|
forceSSL = true;
|
|
enableACME = true;
|
|
locations."/" = {
|
|
proxyPass = "http://${server-config.server.listenaddr}:${toString server-config.server.port}";
|
|
extraConfig = ''
|
|
# Ensuring it can use websockets
|
|
proxy_set_header Upgrade $http_upgrade;
|
|
proxy_set_header Connection "upgrade";
|
|
proxy_set_header X-Real-IP $remote_addr;
|
|
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
|
|
proxy_set_header X-Forwarded-Proto http;
|
|
proxy_redirect http:// $scheme://;
|
|
|
|
# The proxy must preserve the host because gotify verifies the host with the origin
|
|
# for WebSocket connections
|
|
proxy_set_header Host $host;
|
|
|
|
# These sets the timeout so that the websocket can stay alive
|
|
proxy_connect_timeout 1m;
|
|
proxy_send_timeout 1m;
|
|
proxy_read_timeout 1m;
|
|
'';
|
|
};
|
|
};
|
|
|
|
# Database setup
|
|
services.postgresql = {
|
|
enable = true;
|
|
ensureDatabases = [cfg.user];
|
|
ensureUsers = [
|
|
{
|
|
name = cfg.user;
|
|
ensureDBOwnership = true;
|
|
}
|
|
];
|
|
};
|
|
};
|
|
}
|