Goodbye containers.
This commit is contained in:
parent
f1ddca8b18
commit
07cfed44d3
|
@ -1,52 +0,0 @@
|
||||||
{
|
|
||||||
config,
|
|
||||||
container,
|
|
||||||
lib,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.change;
|
|
||||||
in {
|
|
||||||
options.container.module.change = {
|
|
||||||
enable = lib.mkEnableOption "the change detection service";
|
|
||||||
address = lib.mkOption {
|
|
||||||
default = "10.1.0.41";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
port = lib.mkOption {
|
|
||||||
default = 5000;
|
|
||||||
type = lib.types.int;
|
|
||||||
};
|
|
||||||
domain = lib.mkOption {
|
|
||||||
default = "change.${config.container.domain}";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
storage = lib.mkOption {
|
|
||||||
default = "${config.container.storage}/change";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = lib.mkIf cfg.enable {
|
|
||||||
systemd.tmpfiles.rules = container.mkContainerDir cfg [
|
|
||||||
"data"
|
|
||||||
];
|
|
||||||
|
|
||||||
containers.change = container.mkContainer cfg {
|
|
||||||
bindMounts = {
|
|
||||||
"/var/lib/changedetection-io" = {
|
|
||||||
hostPath = "${cfg.storage}/data";
|
|
||||||
isReadOnly = false;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = { ... }: container.mkContainerConfig cfg {
|
|
||||||
services.changedetection-io = {
|
|
||||||
enable = true;
|
|
||||||
baseURL = cfg.domain;
|
|
||||||
behindProxy = true;
|
|
||||||
listenAddress = cfg.address;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,72 +0,0 @@
|
||||||
{
|
|
||||||
config,
|
|
||||||
container,
|
|
||||||
lib,
|
|
||||||
pkgs,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.chat;
|
|
||||||
db = config.container.module.postgres;
|
|
||||||
in {
|
|
||||||
options.container.module.chat = {
|
|
||||||
enable = lib.mkEnableOption "the chat container.";
|
|
||||||
address = lib.mkOption {
|
|
||||||
default = "10.1.0.20";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
port = lib.mkOption {
|
|
||||||
default = 8065;
|
|
||||||
type = lib.types.int;
|
|
||||||
};
|
|
||||||
domain = lib.mkOption {
|
|
||||||
default = "chat.${config.container.domain}";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
storage = lib.mkOption {
|
|
||||||
default = "${config.container.storage}/chat";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
# WIP: https://search.nixos.org/options?channel=24.05&from=0&size=50&sort=relevance&type=packages&query=mattermost
|
|
||||||
config = lib.mkIf cfg.enable {
|
|
||||||
systemd.tmpfiles.rules = container.mkContainerDir cfg [
|
|
||||||
"data"
|
|
||||||
];
|
|
||||||
|
|
||||||
containers.chat = container.mkContainer cfg {
|
|
||||||
bindMounts = {
|
|
||||||
"/var/lib/mattermost" = {
|
|
||||||
hostPath = "${cfg.storage}/data";
|
|
||||||
isReadOnly = false;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = { ... }: container.mkContainerConfig cfg {
|
|
||||||
services.mattermost = {
|
|
||||||
enable = true;
|
|
||||||
listenAddress = ":${toString cfg.port}";
|
|
||||||
localDatabaseCreate = false;
|
|
||||||
mutableConfig = false;
|
|
||||||
package = pkgs.mattermost;
|
|
||||||
siteName = "Chat";
|
|
||||||
siteUrl = "https://${cfg.domain}";
|
|
||||||
statePath = "/var/lib/mattermost";
|
|
||||||
plugins = [
|
|
||||||
(pkgs.fetchurl rec {
|
|
||||||
hash = "sha256-yQGBpBPgXxC+Pm6dHlbwlNEdvn6wg9neSpNNTC4YYAA=";
|
|
||||||
url = "https://github.com/mattermost/mattermost-plugin-calls/releases/download/v${version}/mattermost-plugin-calls-v${version}.tar.gz";
|
|
||||||
version = "1.2.0";
|
|
||||||
})
|
|
||||||
];
|
|
||||||
extraConfig = {
|
|
||||||
SqlSettings = {
|
|
||||||
DataSource = "postgres://mattermost:any@${db.address}:${toString db.port}/mattermost?sslmode=disable&connect_timeout=10";
|
|
||||||
DriverName = "postgres";
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,104 +0,0 @@
|
||||||
{
|
|
||||||
config,
|
|
||||||
container,
|
|
||||||
lib,
|
|
||||||
pkgs,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.cloud;
|
|
||||||
postgres = config.container.module.postgres;
|
|
||||||
proxy = config.container.module.proxy;
|
|
||||||
in {
|
|
||||||
options.container.module.cloud = {
|
|
||||||
enable = lib.mkEnableOption "the file cloud service.";
|
|
||||||
address = lib.mkOption {
|
|
||||||
default = "10.1.0.13";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
port = lib.mkOption {
|
|
||||||
default = 80;
|
|
||||||
type = lib.types.int;
|
|
||||||
};
|
|
||||||
domain = lib.mkOption {
|
|
||||||
default = "cloud.${config.container.domain}";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
storage = lib.mkOption {
|
|
||||||
default = "${config.container.storage}/cloud";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = lib.mkIf cfg.enable {
|
|
||||||
systemd.tmpfiles.rules = container.mkContainerDir cfg [
|
|
||||||
"data"
|
|
||||||
];
|
|
||||||
|
|
||||||
containers.cloud = container.mkContainer cfg {
|
|
||||||
bindMounts = {
|
|
||||||
"/var/lib/nextcloud" = {
|
|
||||||
hostPath = "${cfg.storage}/data";
|
|
||||||
isReadOnly = false;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = { config, ... }: container.mkContainerConfig cfg {
|
|
||||||
services.nextcloud = {
|
|
||||||
enable = true;
|
|
||||||
hostName = cfg.domain;
|
|
||||||
# package = pkgs.nextcloud29;
|
|
||||||
# phpOptions = {
|
|
||||||
# memory_limit = lib.mkForce "20G";
|
|
||||||
# };
|
|
||||||
config = {
|
|
||||||
adminpassFile = "${pkgs.writeText "NextcloudPassword" "root"}";
|
|
||||||
adminuser = "root";
|
|
||||||
dbhost = postgres.address;
|
|
||||||
dbname = "nextcloud";
|
|
||||||
dbpassFile = "${pkgs.writeText "NextcloudDbPassword" "nextcloud"}";
|
|
||||||
dbtype = "pgsql";
|
|
||||||
dbuser = "nextcloud";
|
|
||||||
};
|
|
||||||
extraApps = {
|
|
||||||
inherit (config.services.nextcloud.package.packages.apps)
|
|
||||||
contacts calendar onlyoffice;
|
|
||||||
};
|
|
||||||
extraAppsEnable = true;
|
|
||||||
settings = {
|
|
||||||
allow_local_remote_servers = true;
|
|
||||||
trusted_domains = [
|
|
||||||
cfg.address
|
|
||||||
cfg.domain
|
|
||||||
];
|
|
||||||
trusted_proxies = [
|
|
||||||
proxy.address
|
|
||||||
];
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
# HACK: This is required for TCP postgres connection.
|
|
||||||
systemd = {
|
|
||||||
services = {
|
|
||||||
nextcloud-setup = {
|
|
||||||
serviceConfig.PrivateNetwork = lib.mkForce false;
|
|
||||||
wantedBy = lib.mkForce [ ];
|
|
||||||
};
|
|
||||||
nextcloud-update-db = {
|
|
||||||
serviceConfig.PrivateNetwork = lib.mkForce false;
|
|
||||||
wantedBy = lib.mkForce [ ];
|
|
||||||
};
|
|
||||||
};
|
|
||||||
timers.fixsystemd = {
|
|
||||||
timerConfig = {
|
|
||||||
OnBootSec = 5;
|
|
||||||
Unit = "nextcloud-setup.service";
|
|
||||||
};
|
|
||||||
wantedBy = [
|
|
||||||
"timers.target"
|
|
||||||
];
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,127 +0,0 @@
|
||||||
{
|
|
||||||
config,
|
|
||||||
container,
|
|
||||||
lib,
|
|
||||||
pkgs,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.dns;
|
|
||||||
in {
|
|
||||||
options.container.module.dns = {
|
|
||||||
enable = lib.mkEnableOption "the DNS server.";
|
|
||||||
address = lib.mkOption {
|
|
||||||
default = "10.1.0.6";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
port = lib.mkOption {
|
|
||||||
default = 53;
|
|
||||||
type = lib.types.int;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = lib.mkIf cfg.enable {
|
|
||||||
containers.dns = container.mkContainer cfg {
|
|
||||||
config = { ... }: container.mkContainerConfig cfg {
|
|
||||||
services.blocky = {
|
|
||||||
enable = true;
|
|
||||||
# REF: https://0xerr0r.github.io/blocky/main/configuration/
|
|
||||||
settings = {
|
|
||||||
bootstrapDns = "tcp+udp:1.1.1.1";
|
|
||||||
connectIPVersion = "v4";
|
|
||||||
ports.dns = cfg.port;
|
|
||||||
# httpPort = "80";
|
|
||||||
upstreams.groups = {
|
|
||||||
default = [
|
|
||||||
"https://dns.quad9.net/dns-query"
|
|
||||||
];
|
|
||||||
};
|
|
||||||
caching = {
|
|
||||||
maxItemsCount = 100000;
|
|
||||||
maxTime = "30m";
|
|
||||||
minTime = "5m";
|
|
||||||
prefetchExpires = "2h";
|
|
||||||
prefetchMaxItemsCount = 100000;
|
|
||||||
prefetchThreshold = 5;
|
|
||||||
prefetching = true;
|
|
||||||
};
|
|
||||||
blocking = {
|
|
||||||
blockTTL = "1m";
|
|
||||||
blockType = "zeroIP";
|
|
||||||
loading = {
|
|
||||||
refreshPeriod = "24h";
|
|
||||||
strategy = "blocking";
|
|
||||||
downloads = {
|
|
||||||
attempts = 3;
|
|
||||||
cooldown = "10s";
|
|
||||||
timeout = "5m";
|
|
||||||
};
|
|
||||||
};
|
|
||||||
# SRC: https://oisd.nl
|
|
||||||
# SRC: https://v.firebog.net
|
|
||||||
denylists = {
|
|
||||||
suspicious = [
|
|
||||||
"https://raw.githubusercontent.com/PolishFiltersTeam/KADhosts/master/KADhosts.txt"
|
|
||||||
"https://raw.githubusercontent.com/StevenBlack/hosts/master/hosts" # https://github.com/StevenBlack/hosts
|
|
||||||
"https://v.firebog.net/hosts/static/w3kbl.txt"
|
|
||||||
];
|
|
||||||
ads = [
|
|
||||||
"https://pgl.yoyo.org/adservers/serverlist.php?hostformat=hosts&showintro=0&mimetype=plaintext"
|
|
||||||
"https://raw.githubusercontent.com/bigdargon/hostsVN/master/hosts"
|
|
||||||
"https://v.firebog.net/hosts/AdguardDNS.txt"
|
|
||||||
"https://v.firebog.net/hosts/Admiral.txt"
|
|
||||||
"https://v.firebog.net/hosts/Easylist.txt"
|
|
||||||
];
|
|
||||||
tracking = [
|
|
||||||
"https://hostfiles.frogeye.fr/firstparty-trackers-hosts.txt"
|
|
||||||
"https://v.firebog.net/hosts/Easyprivacy.txt"
|
|
||||||
"https://v.firebog.net/hosts/Prigent-Ads.txt"
|
|
||||||
];
|
|
||||||
malicious = [
|
|
||||||
"https://gitlab.com/quidsup/notrack-blocklists/raw/master/notrack-malware.txt"
|
|
||||||
"https://osint.digitalside.it/Threat-Intel/lists/latestdomains.txt"
|
|
||||||
"https://phishing.army/download/phishing_army_blocklist_extended.txt"
|
|
||||||
"https://raw.githubusercontent.com/AssoEchap/stalkerware-indicators/master/generated/hosts"
|
|
||||||
"https://raw.githubusercontent.com/Spam404/lists/master/main-blacklist.txt"
|
|
||||||
"https://urlhaus.abuse.ch/downloads/hostfile/"
|
|
||||||
"https://v.firebog.net/hosts/Prigent-Crypto.txt"
|
|
||||||
"https://v.firebog.net/hosts/Prigent-Malware.txt"
|
|
||||||
];
|
|
||||||
other = [
|
|
||||||
"https://big.oisd.nl/domainswild"
|
|
||||||
"https://zerodot1.gitlab.io/CoinBlockerLists/hosts_browser"
|
|
||||||
];
|
|
||||||
};
|
|
||||||
# allowlists = {
|
|
||||||
# other = [
|
|
||||||
# "/.*.vk.com/"
|
|
||||||
# ];
|
|
||||||
# };
|
|
||||||
clientGroupsBlock = {
|
|
||||||
default = [
|
|
||||||
"ads"
|
|
||||||
"malicious"
|
|
||||||
"other"
|
|
||||||
"suspicious"
|
|
||||||
"tracking"
|
|
||||||
];
|
|
||||||
};
|
|
||||||
};
|
|
||||||
customDNS = {
|
|
||||||
mapping = let
|
|
||||||
block = host: { ${host} = "0.0.0.0"; };
|
|
||||||
in {
|
|
||||||
# All subdomains to current host.
|
|
||||||
# ${config.container.domain} = config.container.host;
|
|
||||||
"voronind.com" = "10.0.0.1,fd09:8d46:b26::1";
|
|
||||||
}
|
|
||||||
// block "gosuslugi.ru"
|
|
||||||
// block "rutube.ru"
|
|
||||||
// block "vk.com"
|
|
||||||
;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,63 +0,0 @@
|
||||||
{
|
|
||||||
config,
|
|
||||||
container,
|
|
||||||
lib,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.download;
|
|
||||||
in {
|
|
||||||
options.container.module.download = {
|
|
||||||
enable = lib.mkEnableOption "the bit-torrent downloader.";
|
|
||||||
address = lib.mkOption {
|
|
||||||
default = "10.1.0.12";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
port = lib.mkOption {
|
|
||||||
default = 8112;
|
|
||||||
type = lib.types.int;
|
|
||||||
};
|
|
||||||
domain = lib.mkOption {
|
|
||||||
default = "download.${config.container.domain}";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
storage = lib.mkOption {
|
|
||||||
default = "${config.container.storage}/download";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
memLimit = lib.mkOption {
|
|
||||||
default = "4G";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = lib.mkIf cfg.enable {
|
|
||||||
systemd.tmpfiles.rules = container.mkContainerDir cfg [
|
|
||||||
"data"
|
|
||||||
];
|
|
||||||
|
|
||||||
containers.download = container.mkContainer cfg {
|
|
||||||
enableTun = true;
|
|
||||||
bindMounts = {
|
|
||||||
"/var/lib/deluge/.config/deluge" = {
|
|
||||||
hostPath = "${cfg.storage}/data";
|
|
||||||
isReadOnly = false;
|
|
||||||
};
|
|
||||||
}
|
|
||||||
// container.attachMedia "download" false
|
|
||||||
;
|
|
||||||
|
|
||||||
config = { ... }: container.mkContainerConfig cfg {
|
|
||||||
services.deluge = {
|
|
||||||
enable = true;
|
|
||||||
dataDir = "/var/lib/deluge";
|
|
||||||
web.enable = true;
|
|
||||||
};
|
|
||||||
systemd.services.deluged.serviceConfig = {
|
|
||||||
MemoryLimit = cfg.memLimit;
|
|
||||||
Restart = lib.mkForce "always";
|
|
||||||
RuntimeMaxSec = "3h";
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,124 +0,0 @@
|
||||||
{
|
|
||||||
__findFile,
|
|
||||||
config,
|
|
||||||
container,
|
|
||||||
inputs,
|
|
||||||
lib,
|
|
||||||
pkgs,
|
|
||||||
pkgsMaster,
|
|
||||||
util,
|
|
||||||
...
|
|
||||||
} @args: let
|
|
||||||
cfg = config.container.module.frkn;
|
|
||||||
in {
|
|
||||||
options.container.module.frkn = {
|
|
||||||
enable = lib.mkEnableOption "the Allmighty FRKN service.";
|
|
||||||
address = lib.mkOption {
|
|
||||||
default = "10.1.0.69";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
port = lib.mkOption {
|
|
||||||
default = 1080;
|
|
||||||
type = lib.types.int;
|
|
||||||
};
|
|
||||||
torport = lib.mkOption {
|
|
||||||
default = 9150;
|
|
||||||
type = lib.types.int;
|
|
||||||
};
|
|
||||||
xrayport = lib.mkOption {
|
|
||||||
default = 1081;
|
|
||||||
type = lib.types.int;
|
|
||||||
};
|
|
||||||
storage = lib.mkOption {
|
|
||||||
default = "${config.container.storage}/frkn";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = lib.mkIf cfg.enable {
|
|
||||||
systemd.tmpfiles.rules = container.mkContainerDir cfg [
|
|
||||||
"data"
|
|
||||||
];
|
|
||||||
|
|
||||||
containers.frkn = container.mkContainer cfg {
|
|
||||||
bindMounts = {
|
|
||||||
"/data" = {
|
|
||||||
hostPath = "${cfg.storage}/data";
|
|
||||||
isReadOnly = true;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = { ... }: container.mkContainerConfig cfg {
|
|
||||||
disabledModules = [ "services/networking/zapret.nix" ];
|
|
||||||
imports = [ "${inputs.nixpkgsMaster}/nixos/modules/services/networking/zapret.nix" ];
|
|
||||||
|
|
||||||
boot.kernel.sysctl = {
|
|
||||||
"net.ipv4.conf.all.src_valid_mark" = 1;
|
|
||||||
"net.ipv4.ip_forward" = 1;
|
|
||||||
};
|
|
||||||
|
|
||||||
services.zapret = {
|
|
||||||
inherit (config.services.zapret) params;
|
|
||||||
enable = true;
|
|
||||||
package = pkgsMaster.zapret;
|
|
||||||
};
|
|
||||||
|
|
||||||
services = {
|
|
||||||
microsocks = {
|
|
||||||
enable = true;
|
|
||||||
disableLogging = true;
|
|
||||||
ip = cfg.address;
|
|
||||||
port = cfg.port;
|
|
||||||
};
|
|
||||||
|
|
||||||
tor = {
|
|
||||||
enable = true;
|
|
||||||
openFirewall = true;
|
|
||||||
settings = let
|
|
||||||
exclude = "{RU},{UA},{BY},{KZ},{CN},{??}";
|
|
||||||
in {
|
|
||||||
# ExcludeExitNodes = exclude;
|
|
||||||
# ExcludeNodes = exclude;
|
|
||||||
# DNSPort = dnsport;
|
|
||||||
UseBridges = true;
|
|
||||||
ClientTransportPlugin = "obfs4 exec ${pkgs.obfs4}/bin/lyrebird";
|
|
||||||
Bridge = [
|
|
||||||
"obfs4 121.45.140.249:12123 0922E212E33B04F0B7C1E398161E8EDE06734F26 cert=3AQ4iJFAzxzt7a/zgXIiFEs6fvrXInXt1Dtr09DgnpvUzG/iiyRTdXYZKSYpI124Zt3ZUA iat-mode=0"
|
|
||||||
"obfs4 145.239.31.71:10161 882125D15B59BB82BE66F999056CB676D3F061F8 cert=AnD+EvcBMuQDVM7PwW7NgFAzW1M5jDm7DjQtIIcBSjoyAf1FJ2p535rrYL2Kk8POAd0+aw iat-mode=0"
|
|
||||||
"obfs4 79.137.11.45:45072 ECA3197D49A29DDECD4ACBF9BCF15E4987B78137 cert=2FKyLWkPgMNCWxBD3cNOTRxJH3XP+HdStPGKMjJfw2YbvVjihIp3X2BCrtxQya9m5II5XA iat-mode=0"
|
|
||||||
"obfs4 94.103.89.153:4443 5617848964FD6546968B5BF3FFA6C11BCCABE58B cert=tYsmuuTe9phJS0Gh8NKIpkVZP/XKs7gJCqi31o8LClwYetxzFz0fQZgsMwhNcIlZ0HG5LA iat-mode=0"
|
|
||||||
];
|
|
||||||
};
|
|
||||||
|
|
||||||
client = {
|
|
||||||
enable = true;
|
|
||||||
# dns.enable = true;
|
|
||||||
socksListenAddress = {
|
|
||||||
IsolateDestAddr = true;
|
|
||||||
addr = cfg.address;
|
|
||||||
port = cfg.torport;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
xray = {
|
|
||||||
enable = true;
|
|
||||||
settingsFile = "/data/Client.json";
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
systemd = {
|
|
||||||
services.tor.wantedBy = lib.mkForce [ ];
|
|
||||||
|
|
||||||
timers.tor = {
|
|
||||||
timerConfig = {
|
|
||||||
OnBootSec = 5;
|
|
||||||
Unit = "tor.service";
|
|
||||||
};
|
|
||||||
wantedBy = [ "timers.target" ];
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,129 +0,0 @@
|
||||||
{
|
|
||||||
config,
|
|
||||||
container,
|
|
||||||
lib,
|
|
||||||
pkgs,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.git;
|
|
||||||
in {
|
|
||||||
options.container.module.git = {
|
|
||||||
enable = lib.mkEnableOption "the git server.";
|
|
||||||
address = lib.mkOption {
|
|
||||||
default = "10.1.0.8";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
port = lib.mkOption {
|
|
||||||
default = 3000;
|
|
||||||
type = lib.types.int;
|
|
||||||
};
|
|
||||||
portSsh = lib.mkOption {
|
|
||||||
default = 22144;
|
|
||||||
type = lib.types.int;
|
|
||||||
};
|
|
||||||
domain = lib.mkOption {
|
|
||||||
default = "git.${config.container.domain}";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
storage = lib.mkOption {
|
|
||||||
default = "${config.container.storage}/git";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = lib.mkIf cfg.enable {
|
|
||||||
systemd.tmpfiles.rules = container.mkContainerDir cfg [
|
|
||||||
"data"
|
|
||||||
];
|
|
||||||
|
|
||||||
containers.git = container.mkContainer cfg {
|
|
||||||
bindMounts = {
|
|
||||||
"/var/lib/forgejo" = {
|
|
||||||
hostPath = "${cfg.storage}/data";
|
|
||||||
isReadOnly = false;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = { ... }: container.mkContainerConfig cfg {
|
|
||||||
environment.systemPackages = with pkgs; [
|
|
||||||
forgejo
|
|
||||||
];
|
|
||||||
|
|
||||||
services.forgejo = {
|
|
||||||
enable = true;
|
|
||||||
stateDir = "/var/lib/forgejo";
|
|
||||||
|
|
||||||
database = let
|
|
||||||
postgre = config.container.module.postgres;
|
|
||||||
in {
|
|
||||||
createDatabase = false;
|
|
||||||
host = postgre.address;
|
|
||||||
name = "forgejo";
|
|
||||||
port = postgre.port;
|
|
||||||
type = "postgres";
|
|
||||||
user = "forgejo";
|
|
||||||
};
|
|
||||||
|
|
||||||
settings = let
|
|
||||||
gcArgs = "--aggressive --no-cruft --prune=now";
|
|
||||||
gcTimeout = 600;
|
|
||||||
in {
|
|
||||||
"cron.cleanup_actions".ENABLED = true;
|
|
||||||
"cron.update_mirrors".SCHEDULE = "@midnight";
|
|
||||||
"git".GC_ARGS = gcArgs;
|
|
||||||
"git.timeout".GC = gcTimeout;
|
|
||||||
"log".LEVEL = "Error";
|
|
||||||
"repo-archive".ENABLED = false;
|
|
||||||
"repository.issue".MAX_PINNED = 99999;
|
|
||||||
"repository.pull-request".DEFAULT_MERGE_STYLE = "rebase";
|
|
||||||
"service".DISABLE_REGISTRATION = true;
|
|
||||||
"server" = {
|
|
||||||
DOMAIN = cfg.domain;
|
|
||||||
HTTP_ADDR = cfg.address;
|
|
||||||
ROOT_URL = "https://${cfg.domain}";
|
|
||||||
BUILTIN_SSH_SERVER_USER = "git";
|
|
||||||
DISABLE_SSH = false;
|
|
||||||
SSH_PORT = cfg.portSsh;
|
|
||||||
START_SSH_SERVER = true;
|
|
||||||
};
|
|
||||||
"ui" = {
|
|
||||||
AMBIGUOUS_UNICODE_DETECTION = false;
|
|
||||||
};
|
|
||||||
"repository" = {
|
|
||||||
DEFAULT_PRIVATE = "private";
|
|
||||||
DEFAULT_PUSH_CREATE_PRIVATE = true;
|
|
||||||
};
|
|
||||||
"cron" = {
|
|
||||||
ENABLED = true;
|
|
||||||
RUN_AT_START = true;
|
|
||||||
};
|
|
||||||
"cron.git_gc_repos" = {
|
|
||||||
ENABLED = true;
|
|
||||||
ARGS = gcArgs;
|
|
||||||
SCHEDULE = "@midnight";
|
|
||||||
TIMEOUT = gcTimeout;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
systemd = {
|
|
||||||
services = {
|
|
||||||
forgejo = {
|
|
||||||
serviceConfig.PrivateNetwork = lib.mkForce false;
|
|
||||||
wantedBy = lib.mkForce [ ];
|
|
||||||
};
|
|
||||||
};
|
|
||||||
timers.fixsystemd = {
|
|
||||||
timerConfig = {
|
|
||||||
OnBootSec = 5;
|
|
||||||
Unit = "forgejo.service";
|
|
||||||
};
|
|
||||||
wantedBy = [
|
|
||||||
"timers.target"
|
|
||||||
];
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,54 +0,0 @@
|
||||||
{
|
|
||||||
__findFile,
|
|
||||||
config,
|
|
||||||
container,
|
|
||||||
lib,
|
|
||||||
pkgs,
|
|
||||||
util,
|
|
||||||
...
|
|
||||||
} @args: let
|
|
||||||
cfg = config.container.module.home;
|
|
||||||
package = (pkgs.callPackage <package/homer> args);
|
|
||||||
in {
|
|
||||||
options.container.module.home = {
|
|
||||||
enable = lib.mkEnableOption "the dashboard.";
|
|
||||||
address = lib.mkOption {
|
|
||||||
default = "10.1.0.18";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
port = lib.mkOption {
|
|
||||||
default = 80;
|
|
||||||
type = lib.types.int;
|
|
||||||
};
|
|
||||||
domain = lib.mkOption {
|
|
||||||
default = "home.${config.container.domain}";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = lib.mkIf cfg.enable {
|
|
||||||
containers.home = container.mkContainer cfg {
|
|
||||||
config = { ... }: container.mkContainerConfig cfg {
|
|
||||||
environment.systemPackages = [
|
|
||||||
package
|
|
||||||
];
|
|
||||||
systemd.packages = [
|
|
||||||
package
|
|
||||||
];
|
|
||||||
|
|
||||||
services.nginx = {
|
|
||||||
enable = true;
|
|
||||||
virtualHosts.${cfg.domain} = container.mkServer {
|
|
||||||
default = true;
|
|
||||||
root = "${package}";
|
|
||||||
locations = {
|
|
||||||
"/".extraConfig = util.trimTabs ''
|
|
||||||
try_files $uri $uri/index.html;
|
|
||||||
'';
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,119 +0,0 @@
|
||||||
{
|
|
||||||
config,
|
|
||||||
container,
|
|
||||||
lib,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.iot;
|
|
||||||
in {
|
|
||||||
options.container.module.iot = {
|
|
||||||
enable = lib.mkEnableOption "IoT service.";
|
|
||||||
address = lib.mkOption {
|
|
||||||
default = "10.1.0.27";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
port = lib.mkOption {
|
|
||||||
default = 8123;
|
|
||||||
type = lib.types.int;
|
|
||||||
};
|
|
||||||
domain = lib.mkOption {
|
|
||||||
default = "iot.${config.container.domain}";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
storage = lib.mkOption {
|
|
||||||
default = "${config.container.storage}/iot";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = lib.mkIf cfg.enable {
|
|
||||||
systemd.tmpfiles.rules = container.mkContainerDir cfg [
|
|
||||||
"data"
|
|
||||||
];
|
|
||||||
|
|
||||||
containers.iot = container.mkContainer cfg {
|
|
||||||
bindMounts = {
|
|
||||||
"/var/lib/hass" = {
|
|
||||||
hostPath = "${cfg.storage}/data";
|
|
||||||
isReadOnly = false;
|
|
||||||
};
|
|
||||||
"/dev/ttyACM0" = {
|
|
||||||
hostPath = "/dev/ttyACM0";
|
|
||||||
isReadOnly = false;
|
|
||||||
};
|
|
||||||
"/dev/serial/by-id" = {
|
|
||||||
hostPath = "/dev/serial/by-id";
|
|
||||||
isReadOnly = false;
|
|
||||||
};
|
|
||||||
}
|
|
||||||
// container.attachMedia "photo" true
|
|
||||||
;
|
|
||||||
|
|
||||||
allowedDevices = [
|
|
||||||
{
|
|
||||||
modifier = "rwm";
|
|
||||||
node = "/dev/ttyACM0";
|
|
||||||
}
|
|
||||||
];
|
|
||||||
|
|
||||||
config = { ... }: container.mkContainerConfig cfg {
|
|
||||||
# Allow Hass to talk to Zigbee dongle.
|
|
||||||
users.users.hass.extraGroups = [
|
|
||||||
"dialout"
|
|
||||||
"tty"
|
|
||||||
];
|
|
||||||
|
|
||||||
services.home-assistant = {
|
|
||||||
# NOTE: Missing: hacs. Inside hacs: `card-mod`, `Clock Weather Card`, `WallPanel` and `Yandex.Station`.
|
|
||||||
enable = true;
|
|
||||||
# NOTE: Using imperative config because of secrets.
|
|
||||||
config = null;
|
|
||||||
configDir = "/var/lib/hass";
|
|
||||||
extraComponents = [
|
|
||||||
"caldav"
|
|
||||||
"met"
|
|
||||||
"sun"
|
|
||||||
"systemmonitor"
|
|
||||||
"zha"
|
|
||||||
];
|
|
||||||
extraPackages =
|
|
||||||
python3Packages: with python3Packages; [
|
|
||||||
aiodhcpwatcher
|
|
||||||
aiodiscover
|
|
||||||
aiogithubapi
|
|
||||||
arrow
|
|
||||||
async-upnp-client
|
|
||||||
av
|
|
||||||
gtts
|
|
||||||
ha-ffmpeg
|
|
||||||
hassil
|
|
||||||
home-assistant-intents
|
|
||||||
mutagen
|
|
||||||
numpy
|
|
||||||
pymicro-vad
|
|
||||||
pynacl
|
|
||||||
pyspeex-noise
|
|
||||||
python-telegram-bot
|
|
||||||
pyturbojpeg
|
|
||||||
zeroconf
|
|
||||||
];
|
|
||||||
# lovelaceConfig = {
|
|
||||||
# title = "Home IoT control center.";
|
|
||||||
# };
|
|
||||||
};
|
|
||||||
|
|
||||||
# HACK: Delay so that nextcloud calendar can reply on reboot.
|
|
||||||
systemd = {
|
|
||||||
services."home-assistant".wantedBy = lib.mkForce [ ];
|
|
||||||
timers.fixsystemd = {
|
|
||||||
timerConfig = {
|
|
||||||
OnBootSec = 60;
|
|
||||||
Unit = "home-assistant.service";
|
|
||||||
};
|
|
||||||
wantedBy = [ "timers.target" ];
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,79 +0,0 @@
|
||||||
{
|
|
||||||
__findFile,
|
|
||||||
config,
|
|
||||||
container,
|
|
||||||
lib,
|
|
||||||
pkgsJobber,
|
|
||||||
poetry2nixJobber,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.jobber;
|
|
||||||
script = import <package/jobber> {
|
|
||||||
pkgs = pkgsJobber;
|
|
||||||
poetry2nix = poetry2nixJobber;
|
|
||||||
};
|
|
||||||
in {
|
|
||||||
options.container.module.jobber = {
|
|
||||||
enable = lib.mkEnableOption "Stanley - the button pusher.";
|
|
||||||
address = lib.mkOption {
|
|
||||||
default = "10.1.0.32";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
storage = lib.mkOption {
|
|
||||||
default = "${config.container.storage}/jobber";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = lib.mkIf cfg.enable {
|
|
||||||
systemd.tmpfiles.rules = container.mkContainerDir cfg [
|
|
||||||
"data"
|
|
||||||
];
|
|
||||||
|
|
||||||
containers.jobber = container.mkContainer cfg {
|
|
||||||
bindMounts = {
|
|
||||||
"/data" = {
|
|
||||||
hostPath = "${cfg.storage}/data";
|
|
||||||
isReadOnly = true;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
enableTun = true;
|
|
||||||
|
|
||||||
config = { ... }: let
|
|
||||||
packages = [
|
|
||||||
script
|
|
||||||
] ++ (with pkgsJobber; [
|
|
||||||
firefox
|
|
||||||
geckodriver
|
|
||||||
openvpn
|
|
||||||
python311
|
|
||||||
]);
|
|
||||||
in container.mkContainerConfig cfg {
|
|
||||||
networking = lib.mkForce {
|
|
||||||
nameservers = [
|
|
||||||
"10.30.218.2"
|
|
||||||
];
|
|
||||||
};
|
|
||||||
|
|
||||||
systemd.services.jobber = {
|
|
||||||
description = "My job is pushing the button.";
|
|
||||||
enable = true;
|
|
||||||
path = packages;
|
|
||||||
wantedBy = [
|
|
||||||
"multi-user.target"
|
|
||||||
];
|
|
||||||
environment = {
|
|
||||||
PYTHONDONTWRITEBYTECODE = "1";
|
|
||||||
PYTHONUNBUFFERED = "1";
|
|
||||||
};
|
|
||||||
serviceConfig = {
|
|
||||||
ExecStart = "${script}/bin/jobber -u";
|
|
||||||
Restart = "on-failure";
|
|
||||||
Type = "simple";
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,224 +0,0 @@
|
||||||
# Guide: https://nixos-mailserver.readthedocs.io/en/latest/setup-guide.html
|
|
||||||
{
|
|
||||||
config,
|
|
||||||
const,
|
|
||||||
container,
|
|
||||||
lib,
|
|
||||||
pkgs,
|
|
||||||
util,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.mail;
|
|
||||||
domain = config.container.domain;
|
|
||||||
in {
|
|
||||||
options.container.module.mail = {
|
|
||||||
enable = lib.mkEnableOption "the email server.";
|
|
||||||
address = lib.mkOption {
|
|
||||||
default = "10.1.0.5";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
port = lib.mkOption {
|
|
||||||
default = 80;
|
|
||||||
type = lib.types.int;
|
|
||||||
};
|
|
||||||
domain = lib.mkOption {
|
|
||||||
default = "mail.${config.container.domain}";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
storage = lib.mkOption {
|
|
||||||
default = "${config.container.storage}/mail";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = lib.mkIf cfg.enable {
|
|
||||||
systemd.tmpfiles.rules = container.mkContainerDir cfg [
|
|
||||||
"data"
|
|
||||||
];
|
|
||||||
|
|
||||||
containers.mail = container.mkContainer cfg {
|
|
||||||
bindMounts = {
|
|
||||||
"/var/lib/dovecot/indices" = {
|
|
||||||
hostPath = "${cfg.storage}/data/indices";
|
|
||||||
isReadOnly = false;
|
|
||||||
};
|
|
||||||
"/var/vmail" = {
|
|
||||||
hostPath = "${cfg.storage}/data/vmail";
|
|
||||||
isReadOnly = false;
|
|
||||||
};
|
|
||||||
"/var/sieve" = {
|
|
||||||
hostPath = "${cfg.storage}/data/sieve";
|
|
||||||
isReadOnly = false;
|
|
||||||
};
|
|
||||||
"/var/dkim" = {
|
|
||||||
hostPath = "${cfg.storage}/data/dkim";
|
|
||||||
isReadOnly = false;
|
|
||||||
};
|
|
||||||
"/acme" = {
|
|
||||||
hostPath = "${config.container.module.proxy.storage}/letsencrypt";
|
|
||||||
isReadOnly = true;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = { config, ... }: container.mkContainerConfig cfg {
|
|
||||||
imports = [
|
|
||||||
(builtins.fetchTarball {
|
|
||||||
sha256 = "sha256:0clvw4622mqzk1aqw1qn6shl9pai097q62mq1ibzscnjayhp278b";
|
|
||||||
url = "https://gitlab.com/simple-nixos-mailserver/nixos-mailserver/-/archive/nixos-${const.stateVersion}/nixos-mailserver-nixos-${const.stateVersion}.tar.gz";
|
|
||||||
})
|
|
||||||
];
|
|
||||||
|
|
||||||
mailserver = {
|
|
||||||
enable = true;
|
|
||||||
domains = [ domain ];
|
|
||||||
fqdn = cfg.domain;
|
|
||||||
sendingFqdn = domain;
|
|
||||||
|
|
||||||
# Use `mkpasswd -sm bcrypt`.
|
|
||||||
loginAccounts = let
|
|
||||||
defaultQuota = "1G";
|
|
||||||
in {
|
|
||||||
"admin@${domain}" = {
|
|
||||||
hashedPassword = "$2b$05$1O.dxXxaVshcBNybcqDRYuTlnYt3jDBwfPZWoDtP4BjOLoL0StYsi";
|
|
||||||
name = "admin";
|
|
||||||
quota = defaultQuota;
|
|
||||||
};
|
|
||||||
"account@${domain}" = {
|
|
||||||
hashedPassword = "$2b$05$sCyZHdk98KqQ1qsTIvbrUeRJlNBOwBqDgpdc1QxiSnONlEkZ8xGNO";
|
|
||||||
name = "account";
|
|
||||||
quota = defaultQuota;
|
|
||||||
};
|
|
||||||
"hi@${domain}" = {
|
|
||||||
hashedPassword = "$2b$05$6fT5hIhzIasNfp9IQr/ds.5RuxH95VKU3QJWlX3hmrAzDF3mExanq";
|
|
||||||
name = "hi";
|
|
||||||
quota = defaultQuota;
|
|
||||||
aliases = [
|
|
||||||
"voronind@${domain}"
|
|
||||||
];
|
|
||||||
};
|
|
||||||
"job@${domain}" = {
|
|
||||||
hashedPassword = "$2b$05$.sUmv2.9EWPfLwJn/oZw2e1UbR7HrpNQ2THc5jjX3ysy7CY8ZWHUC";
|
|
||||||
name = "job";
|
|
||||||
quota = defaultQuota;
|
|
||||||
};
|
|
||||||
"trash@${domain}" = {
|
|
||||||
hashedPassword = "$2b$05$kn5ygZjN9NR3LXjnKKRw/.DXaZQNW.1XEottlCFIoKiDpIj.JGLJm";
|
|
||||||
name = "trash";
|
|
||||||
quota = defaultQuota;
|
|
||||||
catchAll = [
|
|
||||||
domain
|
|
||||||
];
|
|
||||||
};
|
|
||||||
"noreply@${domain}" = {
|
|
||||||
hashedPassword = "$2b$05$TaKwoYmcmkAhsRRv6xG5wOkChcz50cB9BP6QPUDKNAcxMbrY6AeMK";
|
|
||||||
name = "noreply";
|
|
||||||
quota = defaultQuota;
|
|
||||||
sendOnly = true;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
enableImap = true;
|
|
||||||
enableImapSsl = true;
|
|
||||||
enableSubmission = true;
|
|
||||||
enableSubmissionSsl = true;
|
|
||||||
|
|
||||||
enableManageSieve = true;
|
|
||||||
virusScanning = false;
|
|
||||||
|
|
||||||
certificateFile = "/acme/live/${domain}/cert.pem";
|
|
||||||
certificateScheme = "manual";
|
|
||||||
keyFile = "/acme/live/${domain}/privkey.pem";
|
|
||||||
|
|
||||||
dkimKeyDirectory = "/var/dkim";
|
|
||||||
indexDir = "/var/lib/dovecot/indices";
|
|
||||||
mailDirectory = "/var/vmail";
|
|
||||||
sieveDirectory = "/var/sieve";
|
|
||||||
|
|
||||||
mailboxes = let
|
|
||||||
mkSpecialBox = specialUse: {
|
|
||||||
${specialUse} = {
|
|
||||||
inherit specialUse;
|
|
||||||
auto = "subscribe";
|
|
||||||
};
|
|
||||||
};
|
|
||||||
in builtins.foldl' (acc: box: acc // (mkSpecialBox box)) {} [
|
|
||||||
"All"
|
|
||||||
"Archive"
|
|
||||||
"Drafts"
|
|
||||||
"Junk"
|
|
||||||
"Sent"
|
|
||||||
"Trash"
|
|
||||||
];
|
|
||||||
|
|
||||||
dmarcReporting = {
|
|
||||||
inherit domain;
|
|
||||||
enable = true;
|
|
||||||
organizationName = "voronind";
|
|
||||||
# email = "noreply@${domain}";
|
|
||||||
};
|
|
||||||
|
|
||||||
# monitoring = {
|
|
||||||
# enable = true;
|
|
||||||
# alertAddress = "admin@${domain}";
|
|
||||||
# };
|
|
||||||
};
|
|
||||||
|
|
||||||
services = {
|
|
||||||
roundcube = {
|
|
||||||
enable = true;
|
|
||||||
hostName = cfg.domain;
|
|
||||||
dicts = with pkgs.aspellDicts; [
|
|
||||||
en
|
|
||||||
ru
|
|
||||||
];
|
|
||||||
plugins = [
|
|
||||||
"managesieve"
|
|
||||||
];
|
|
||||||
extraConfig = util.trimTabs ''
|
|
||||||
$config['smtp_server'] = "localhost:25";
|
|
||||||
$config['smtp_auth_type'] = null;
|
|
||||||
$config['smtp_user'] = "";
|
|
||||||
$config['smtp_pass'] = "";
|
|
||||||
# $config['smtp_user'] = "%u";
|
|
||||||
# $config['smtp_pass'] = "%p";
|
|
||||||
'';
|
|
||||||
};
|
|
||||||
|
|
||||||
nginx.virtualHosts.${cfg.domain} = {
|
|
||||||
enableACME = false;
|
|
||||||
forceSSL = false;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
systemd = {
|
|
||||||
services.autoexpunge = {
|
|
||||||
description = "Delete old mail";
|
|
||||||
serviceConfig = {
|
|
||||||
Type = "oneshot";
|
|
||||||
};
|
|
||||||
path = [
|
|
||||||
pkgs.dovecot
|
|
||||||
];
|
|
||||||
script = util.trimTabs ''
|
|
||||||
doveadm expunge -A mailbox Junk SENTBEFORE 7d
|
|
||||||
doveadm expunge -A mailbox Trash SENTBEFORE 30d
|
|
||||||
doveadm expunge -u trash@voronind.com mailbox Inbox SENTBEFORE 30d
|
|
||||||
doveadm purge -A
|
|
||||||
'';
|
|
||||||
};
|
|
||||||
|
|
||||||
timers.autoexpunge = {
|
|
||||||
timerConfig = {
|
|
||||||
OnCalendar = "daily";
|
|
||||||
Persistent = true;
|
|
||||||
Unit = "autoexpunge.service";
|
|
||||||
};
|
|
||||||
wantedBy = [
|
|
||||||
"timers.target"
|
|
||||||
];
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,101 +0,0 @@
|
||||||
# NOTE: Imperative part:
|
|
||||||
# 1. You need to change PSQL tables owner from root to onlyoffice, too. They don't do that automatically for some reason.
|
|
||||||
# 2. TODO: Generate JWT secret at /var/lib/onlyoffice/jwt, i.e. 9wLfMGha1YrfvWpb5hyYjZf8pvJQ3swS
|
|
||||||
# See https://git.voronind.com/voronind/nixos/issues/74
|
|
||||||
{
|
|
||||||
config,
|
|
||||||
container,
|
|
||||||
lib,
|
|
||||||
pkgs,
|
|
||||||
util,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.office;
|
|
||||||
in {
|
|
||||||
options.container.module.office = {
|
|
||||||
enable = lib.mkEnableOption "the office web suite.";
|
|
||||||
address = lib.mkOption {
|
|
||||||
default = "10.1.0.21";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
port = lib.mkOption {
|
|
||||||
default = 8000;
|
|
||||||
type = lib.types.int;
|
|
||||||
};
|
|
||||||
domain = lib.mkOption {
|
|
||||||
default = "office.${config.container.domain}";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
storage = lib.mkOption {
|
|
||||||
default = "${config.container.storage}/office";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = lib.mkIf cfg.enable {
|
|
||||||
systemd.tmpfiles.rules = container.mkContainerDir cfg [
|
|
||||||
"data"
|
|
||||||
];
|
|
||||||
|
|
||||||
containers.office = container.mkContainer cfg {
|
|
||||||
bindMounts = {
|
|
||||||
"/var/lib/onlyoffice" = {
|
|
||||||
hostPath = "${cfg.storage}/data";
|
|
||||||
isReadOnly = false;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
# HACK: Temporarely run in docker due to https://github.com/ONLYOFFICE/onlyoffice-nextcloud/issues/931
|
|
||||||
config = { pkgs, ... }: container.mkContainerConfig cfg {
|
|
||||||
virtualisation.oci-containers.backend = "docker";
|
|
||||||
virtualisation.oci-containers.containers.office = {
|
|
||||||
autoStart = true;
|
|
||||||
image = "dockerhub.timeweb.cloud/onlyoffice/documentserver:latest";
|
|
||||||
# ports = [ "${toString cfg.port}:8000" ];
|
|
||||||
extraOptions = [
|
|
||||||
"--network=host"
|
|
||||||
"--privileged"
|
|
||||||
];
|
|
||||||
environment = {
|
|
||||||
AMQP_URI = "amqp://guest:guest@${config.container.module.rabbitmq.address}:${toString config.container.module.rabbitmq.port}";
|
|
||||||
DB_HOST = config.container.module.postgres.address;
|
|
||||||
DB_NAME = "onlyoffice";
|
|
||||||
DB_PORT = toString config.container.module.postgres.port;
|
|
||||||
DB_PWD = "onlyoffice";
|
|
||||||
DB_USER = "onlyoffice";
|
|
||||||
JWT_ENABLED = "true";
|
|
||||||
JWT_SECRET = "8wLfKGha8YRfvwpB5hYYjZf8vtUQs3wS";
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
# config = { pkgs, ... }: container.mkContainerConfig cfg {
|
|
||||||
# # HACK: For whatever reason it does not detect my global allowUnfree (I pass pkgs from host system in mkContainerConfig).
|
|
||||||
# nixpkgs.overlays = [ (final: prev: {
|
|
||||||
# corefonts = prev.corefonts.overrideAttrs (old: {
|
|
||||||
# meta.license = mkForce licenses.mit;
|
|
||||||
# });
|
|
||||||
# })];
|
|
||||||
|
|
||||||
# services.onlyoffice = let
|
|
||||||
# dbName = "onlyoffice";
|
|
||||||
# in {
|
|
||||||
# enable = true;
|
|
||||||
# hostname = cfg.domain;
|
|
||||||
|
|
||||||
# postgresName = dbName;
|
|
||||||
# postgresHost = config.container.module.postgres.address;
|
|
||||||
# postgresUser = dbName;
|
|
||||||
# postgresPasswordFile = "${pkgs.writeText "OfficeDbPassword" dbName}";
|
|
||||||
|
|
||||||
# jwtSecretFile = "/var/lib/onlyoffice/jwt";
|
|
||||||
|
|
||||||
# rabbitmqUrl = "amqp://guest:guest@${config.container.module.rabbitmq.address}:${toString config.container.module.rabbitmq.port}";
|
|
||||||
|
|
||||||
# examplePort = cfg.port;
|
|
||||||
# enableExampleServer = true;
|
|
||||||
# };
|
|
||||||
# };
|
|
||||||
};
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,99 +0,0 @@
|
||||||
{
|
|
||||||
config,
|
|
||||||
container,
|
|
||||||
lib,
|
|
||||||
pkgs,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.paper;
|
|
||||||
in {
|
|
||||||
options.container.module.paper = {
|
|
||||||
enable = lib.mkEnableOption "the paper scans manager.";
|
|
||||||
address = lib.mkOption {
|
|
||||||
default = "10.1.0.40";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
port = lib.mkOption {
|
|
||||||
default = 28981;
|
|
||||||
type = lib.types.int;
|
|
||||||
};
|
|
||||||
domain = lib.mkOption {
|
|
||||||
default = "paper.${config.container.domain}";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
storage = lib.mkOption {
|
|
||||||
default = "${config.container.storage}/paper";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = lib.mkIf cfg.enable {
|
|
||||||
systemd.tmpfiles.rules = container.mkContainerDir cfg [
|
|
||||||
"data"
|
|
||||||
];
|
|
||||||
|
|
||||||
containers.paper = container.mkContainer cfg {
|
|
||||||
bindMounts = {
|
|
||||||
"/var/lib/paperless" = {
|
|
||||||
hostPath = "${cfg.storage}/data";
|
|
||||||
isReadOnly = false;
|
|
||||||
};
|
|
||||||
"/var/lib/paperless/media" = {
|
|
||||||
hostPath = "${lib.elemAt config.container.media.paper 0}";
|
|
||||||
isReadOnly = false;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = { ... }: container.mkContainerConfig cfg {
|
|
||||||
services.paperless = {
|
|
||||||
enable = true;
|
|
||||||
address = "0.0.0.0";
|
|
||||||
dataDir = "/var/lib/paperless";
|
|
||||||
port = cfg.port;
|
|
||||||
passwordFile = pkgs.writeText "PaperlessPassword" "root"; # NOTE: Only for initial setup, change later.
|
|
||||||
settings = {
|
|
||||||
PAPERLESS_ADMIN_USER = "root";
|
|
||||||
PAPERLESS_DBENGINE = "postgresql";
|
|
||||||
PAPERLESS_DBHOST = config.container.module.postgres.address;
|
|
||||||
PAPERLESS_DBNAME = "paperless";
|
|
||||||
PAPERLESS_DBPASS = "paperless";
|
|
||||||
PAPERLESS_DBPORT = config.container.module.postgres.port;
|
|
||||||
PAPERLESS_DBUSER = "paperless";
|
|
||||||
PAPERLESS_OCR_LANGUAGE = "rus";
|
|
||||||
PAPERLESS_REDIS = "redis://${config.container.module.redis.address}:${toString config.container.module.redis.port}";
|
|
||||||
PAPERLESS_URL = "https://${cfg.domain}";
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
# HACK: This is required for TCP postgres connection.
|
|
||||||
systemd = {
|
|
||||||
services = {
|
|
||||||
paperless-scheduler = {
|
|
||||||
serviceConfig.PrivateNetwork = lib.mkForce false;
|
|
||||||
wantedBy = lib.mkForce [ ];
|
|
||||||
};
|
|
||||||
paperless-consumer = {
|
|
||||||
serviceConfig.PrivateNetwork = lib.mkForce false;
|
|
||||||
wantedBy = lib.mkForce [ ];
|
|
||||||
};
|
|
||||||
paperless-web = {
|
|
||||||
wantedBy = lib.mkForce [ ];
|
|
||||||
};
|
|
||||||
paperless-task-queue = {
|
|
||||||
wantedBy = lib.mkForce [ ];
|
|
||||||
};
|
|
||||||
};
|
|
||||||
timers.fixsystemd = {
|
|
||||||
timerConfig = {
|
|
||||||
OnBootSec = 5;
|
|
||||||
Unit = "paperless-web.service";
|
|
||||||
};
|
|
||||||
wantedBy = [
|
|
||||||
"timers.target"
|
|
||||||
];
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,59 +0,0 @@
|
||||||
{
|
|
||||||
config,
|
|
||||||
container,
|
|
||||||
lib,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.pass;
|
|
||||||
in {
|
|
||||||
options.container.module.pass = {
|
|
||||||
enable = lib.mkEnableOption "the password manager.";
|
|
||||||
address = lib.mkOption {
|
|
||||||
default = "10.1.0.9";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
port = lib.mkOption {
|
|
||||||
default = 8000;
|
|
||||||
type = lib.types.int;
|
|
||||||
};
|
|
||||||
domain = lib.mkOption {
|
|
||||||
default = "pass.${config.container.domain}";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
storage = lib.mkOption {
|
|
||||||
default = "${config.container.storage}/pass";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = lib.mkIf cfg.enable {
|
|
||||||
systemd.tmpfiles.rules = container.mkContainerDir cfg [
|
|
||||||
"data"
|
|
||||||
];
|
|
||||||
|
|
||||||
containers.pass = container.mkContainer cfg {
|
|
||||||
bindMounts = {
|
|
||||||
"/var/lib/vaultwarden" = {
|
|
||||||
hostPath = "${cfg.storage}/data";
|
|
||||||
isReadOnly = false;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = { ... }: container.mkContainerConfig cfg {
|
|
||||||
services.vaultwarden = {
|
|
||||||
enable = true;
|
|
||||||
dbBackend = "sqlite";
|
|
||||||
environmentFile = "/var/lib/vaultwarden/Env";
|
|
||||||
config = {
|
|
||||||
DATA_FOLDER = "/var/lib/vaultwarden";
|
|
||||||
DOMAIN = "http://${cfg.domain}";
|
|
||||||
ROCKET_ADDRESS = cfg.address;
|
|
||||||
ROCKET_PORT = cfg.port;
|
|
||||||
SIGNUPS_ALLOWED = false;
|
|
||||||
WEB_VAULT_ENABLED = true;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,134 +0,0 @@
|
||||||
{
|
|
||||||
__findFile,
|
|
||||||
config,
|
|
||||||
container,
|
|
||||||
lib,
|
|
||||||
pkgs,
|
|
||||||
util,
|
|
||||||
...
|
|
||||||
} @args: let
|
|
||||||
cfg = config.container.module.paste;
|
|
||||||
package = (pkgs.callPackage <package/privatebin> args);
|
|
||||||
in {
|
|
||||||
options.container.module.paste = {
|
|
||||||
enable = lib.mkEnableOption "the text share platform.";
|
|
||||||
address = lib.mkOption {
|
|
||||||
default = "10.1.0.14";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
port = lib.mkOption {
|
|
||||||
default = 80;
|
|
||||||
type = lib.types.int;
|
|
||||||
};
|
|
||||||
domain = lib.mkOption {
|
|
||||||
default = "paste.${config.container.domain}";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
storage = lib.mkOption {
|
|
||||||
default = "${config.container.storage}/paste";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = lib.mkIf cfg.enable {
|
|
||||||
systemd.tmpfiles.rules = container.mkContainerDir cfg [
|
|
||||||
"config"
|
|
||||||
"data"
|
|
||||||
"nginxtmp"
|
|
||||||
"tmp"
|
|
||||||
];
|
|
||||||
|
|
||||||
containers.paste = container.mkContainer cfg {
|
|
||||||
bindMounts = {
|
|
||||||
"/srv/data" = {
|
|
||||||
hostPath = "${cfg.storage}/data";
|
|
||||||
isReadOnly = false;
|
|
||||||
};
|
|
||||||
"/tmp" = {
|
|
||||||
hostPath = "${cfg.storage}/tmp";
|
|
||||||
isReadOnly = false;
|
|
||||||
};
|
|
||||||
"/var/lib/nginx/tmp" = {
|
|
||||||
hostPath = "${cfg.storage}/nginxtmp";
|
|
||||||
isReadOnly = false;
|
|
||||||
};
|
|
||||||
"/srv/config" = {
|
|
||||||
hostPath = "${cfg.storage}/config";
|
|
||||||
isReadOnly = false;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = { config, ... }: container.mkContainerConfig cfg {
|
|
||||||
environment.systemPackages = [
|
|
||||||
package
|
|
||||||
];
|
|
||||||
systemd.packages = [
|
|
||||||
package
|
|
||||||
];
|
|
||||||
|
|
||||||
users.users.paste = {
|
|
||||||
group = "nginx";
|
|
||||||
isSystemUser = true;
|
|
||||||
};
|
|
||||||
|
|
||||||
services = {
|
|
||||||
phpfpm.pools.paste = {
|
|
||||||
group = "nginx";
|
|
||||||
user = "paste";
|
|
||||||
phpPackage = pkgs.php;
|
|
||||||
settings = {
|
|
||||||
"catch_workers_output" = true;
|
|
||||||
"listen.owner" = "nginx";
|
|
||||||
"php_admin_flag[log_errors]" = true;
|
|
||||||
"php_admin_value[error_log]" = "stderr";
|
|
||||||
"pm" = "dynamic";
|
|
||||||
"pm.max_children" = "32";
|
|
||||||
"pm.max_requests" = "500";
|
|
||||||
"pm.max_spare_servers" = "4";
|
|
||||||
"pm.min_spare_servers" = "2";
|
|
||||||
"pm.start_servers" = "2";
|
|
||||||
};
|
|
||||||
phpEnv = {
|
|
||||||
# CONFIG_PATH = "${package}/cfg"; # NOTE: Not working?
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
nginx = {
|
|
||||||
enable = true;
|
|
||||||
virtualHosts.${cfg.domain} = container.mkServer {
|
|
||||||
default = true;
|
|
||||||
root = "${package}";
|
|
||||||
locations = {
|
|
||||||
"/".extraConfig = util.trimTabs ''
|
|
||||||
rewrite ^ /index.php;
|
|
||||||
'';
|
|
||||||
|
|
||||||
"~ \\.php$".extraConfig = util.trimTabs ''
|
|
||||||
fastcgi_split_path_info ^(.+\.php)(/.+)$;
|
|
||||||
fastcgi_pass unix:${config.services.phpfpm.pools.paste.socket};
|
|
||||||
include ${config.services.nginx.package}/conf/fastcgi.conf;
|
|
||||||
include ${config.services.nginx.package}/conf/fastcgi_params;
|
|
||||||
'';
|
|
||||||
|
|
||||||
"~ \\.(js|css|ttf|woff2?|png|jpe?g|svg)$".extraConfig = util.trimTabs ''
|
|
||||||
add_header Cache-Control "public, max-age=15778463";
|
|
||||||
add_header Referrer-Policy no-referrer;
|
|
||||||
add_header X-Content-Type-Options nosniff;
|
|
||||||
add_header X-Download-Options noopen;
|
|
||||||
add_header X-Permitted-Cross-Domain-Policies none;
|
|
||||||
add_header X-Robots-Tag none;
|
|
||||||
add_header X-XSS-Protection "1; mode=block";
|
|
||||||
access_log off;
|
|
||||||
'';
|
|
||||||
};
|
|
||||||
|
|
||||||
extraConfig = util.trimTabs ''
|
|
||||||
try_files $uri /index.php;
|
|
||||||
'';
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,95 +0,0 @@
|
||||||
{
|
|
||||||
config,
|
|
||||||
container,
|
|
||||||
lib,
|
|
||||||
pkgs,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.postgres;
|
|
||||||
in {
|
|
||||||
options.container.module.postgres = {
|
|
||||||
enable = lib.mkEnableOption "the PostgreSQL server.";
|
|
||||||
address = lib.mkOption {
|
|
||||||
default = "10.1.0.3";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
port = lib.mkOption {
|
|
||||||
default = 5432;
|
|
||||||
type = lib.types.int;
|
|
||||||
};
|
|
||||||
storage = lib.mkOption {
|
|
||||||
default = "${config.container.storage}/postgres";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = lib.mkIf cfg.enable {
|
|
||||||
systemd.tmpfiles.rules = container.mkContainerDir cfg [
|
|
||||||
"data"
|
|
||||||
];
|
|
||||||
|
|
||||||
containers.postgres = container.mkContainer cfg {
|
|
||||||
bindMounts = {
|
|
||||||
"/var/lib/postgresql/data" = {
|
|
||||||
hostPath = "${cfg.storage}/data";
|
|
||||||
isReadOnly = false;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = { ... }: container.mkContainerConfig cfg {
|
|
||||||
services.postgresql = let
|
|
||||||
# Populate with services here.
|
|
||||||
configurations = with config.container.module; {
|
|
||||||
forgejo = git;
|
|
||||||
invidious = yt;
|
|
||||||
mattermost = chat;
|
|
||||||
nextcloud = cloud;
|
|
||||||
onlyoffice = office;
|
|
||||||
paperless = paper;
|
|
||||||
privatebin = paste;
|
|
||||||
};
|
|
||||||
|
|
||||||
access = configurations // {
|
|
||||||
all.address = config.container.host;
|
|
||||||
};
|
|
||||||
|
|
||||||
authentication = let
|
|
||||||
rules = lib.mapAttrsToList (db: cfg:
|
|
||||||
"host ${db} ${db} ${cfg.address}/32 trust"
|
|
||||||
) access;
|
|
||||||
in builtins.foldl' (acc: item: acc + "${item}\n") "" rules;
|
|
||||||
|
|
||||||
ensureDatabases = [
|
|
||||||
"root"
|
|
||||||
] ++ lib.mapAttrsToList (name: _: name) configurations;
|
|
||||||
|
|
||||||
ensureUsers = map (name: {
|
|
||||||
inherit name;
|
|
||||||
ensureDBOwnership = true;
|
|
||||||
ensureClauses = if name == "root" then {
|
|
||||||
createdb = true;
|
|
||||||
createrole = true;
|
|
||||||
superuser = true;
|
|
||||||
} else { };
|
|
||||||
}) ensureDatabases;
|
|
||||||
in {
|
|
||||||
inherit authentication ensureDatabases ensureUsers;
|
|
||||||
|
|
||||||
enable = true;
|
|
||||||
dataDir = "/var/lib/postgresql/data/14";
|
|
||||||
enableTCPIP = true;
|
|
||||||
package = pkgs.postgresql_14;
|
|
||||||
|
|
||||||
# NOTE: Debug mode.
|
|
||||||
# settings = {
|
|
||||||
# log_connections = true;
|
|
||||||
# log_destination = lib.mkForce "syslog";
|
|
||||||
# log_disconnections = true;
|
|
||||||
# log_statement = "all";
|
|
||||||
# logging_collector = true;
|
|
||||||
# };
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,72 +0,0 @@
|
||||||
# NOTE: Login to contaier, run passwd and use that root/pw combo for administration. `AllowFrom = all` doesn't seem to work.
|
|
||||||
# ipp://192.168.2.237
|
|
||||||
# Pantum M6500W-Series
|
|
||||||
{
|
|
||||||
__findFile,
|
|
||||||
config,
|
|
||||||
container,
|
|
||||||
lib,
|
|
||||||
pkgs,
|
|
||||||
...
|
|
||||||
} @args: let
|
|
||||||
cfg = config.container.module.print;
|
|
||||||
host = config.container.host;
|
|
||||||
package = pkgs.callPackage <package/print> args;
|
|
||||||
in {
|
|
||||||
options.container.module.print = {
|
|
||||||
enable = lib.mkEnableOption "the printing server.";
|
|
||||||
address = lib.mkOption {
|
|
||||||
default = "10.1.0.46";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
port = lib.mkOption {
|
|
||||||
default = 631;
|
|
||||||
type = lib.types.int;
|
|
||||||
};
|
|
||||||
domain = lib.mkOption {
|
|
||||||
default = "print.${config.container.domain}";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
storage = lib.mkOption {
|
|
||||||
default = "${config.container.storage}/print";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = lib.mkIf cfg.enable {
|
|
||||||
systemd.tmpfiles.rules = container.mkContainerDir cfg [
|
|
||||||
"data"
|
|
||||||
];
|
|
||||||
|
|
||||||
containers.print = container.mkContainer cfg {
|
|
||||||
bindMounts = {
|
|
||||||
"/var/lib/cups" = {
|
|
||||||
hostPath = "${cfg.storage}/data";
|
|
||||||
isReadOnly = false;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = { ... }: container.mkContainerConfig cfg {
|
|
||||||
networking.interfaces."eth0".ipv4.routes = [
|
|
||||||
{
|
|
||||||
address = "192.168.2.237"; # NOTE: Printer's IP address.
|
|
||||||
prefixLength = 32;
|
|
||||||
via = host;
|
|
||||||
}
|
|
||||||
];
|
|
||||||
|
|
||||||
services.printing = {
|
|
||||||
enable = true;
|
|
||||||
allowFrom = [ "all" ];
|
|
||||||
browsing = true;
|
|
||||||
defaultShared = true;
|
|
||||||
drivers = [ package ];
|
|
||||||
listenAddresses = [ "${cfg.address}:${toString cfg.port}" ];
|
|
||||||
startWhenNeeded = true;
|
|
||||||
stateless = false;
|
|
||||||
webInterface = true;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,94 +0,0 @@
|
||||||
# NOTE: To generate self-signed certs use: `openssl req -x509 -nodes -days 365 -newkey rsa:2048 -keyout ./privkey.pem -out ./fullchain.pem`
|
|
||||||
# For dhparams: `openssl dhparam -out ./ssl-dhparam.pem 4096`
|
|
||||||
# Example for options-ssl-nginx.conf:
|
|
||||||
# ```
|
|
||||||
# ssl_session_cache shared:le_nginx_SSL:10m;
|
|
||||||
# ssl_session_timeout 1440m;
|
|
||||||
# ssl_protocols TLSv1.2 TLSv1.3;
|
|
||||||
# ssl_prefer_server_ciphers off;
|
|
||||||
# ssl_ciphers "ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-CHACHA20-POLY1305:ECDHE-RSA-CHACHA20-POLY1305:DHE-RSA-AES128-GCM-SHA256:DHE-RSA-AES256-GCM-SHA384";
|
|
||||||
# ```
|
|
||||||
# For certbot to generate new keys: `certbot certonly --manual --manual-public-ip-logging-ok --preferred-challenges dns-01 --server https://acme-v02.api.letsencrypt.org/directory -d "*.voronind.com" -d voronind.com`
|
|
||||||
{
|
|
||||||
config,
|
|
||||||
container,
|
|
||||||
lib,
|
|
||||||
pkgs,
|
|
||||||
util,
|
|
||||||
...
|
|
||||||
} @args: let
|
|
||||||
cfg = config.container.module.proxy;
|
|
||||||
virtualHosts = util.catSet (util.ls ./proxy/host) args;
|
|
||||||
in {
|
|
||||||
options.container.module.proxy = {
|
|
||||||
enable = lib.mkEnableOption "the proxy server.";
|
|
||||||
address = lib.mkOption {
|
|
||||||
default = "10.1.0.2";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
port = lib.mkOption {
|
|
||||||
default = 443;
|
|
||||||
type = lib.types.int;
|
|
||||||
};
|
|
||||||
storage = lib.mkOption {
|
|
||||||
default = "${config.container.storage}/proxy";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = lib.mkIf cfg.enable {
|
|
||||||
systemd.tmpfiles.rules = container.mkContainerDir cfg [
|
|
||||||
"challenge"
|
|
||||||
"letsencrypt"
|
|
||||||
];
|
|
||||||
|
|
||||||
containers.proxy = container.mkContainer cfg {
|
|
||||||
bindMounts = {
|
|
||||||
"/etc/letsencrypt" = {
|
|
||||||
hostPath = "${cfg.storage}/letsencrypt";
|
|
||||||
isReadOnly = false;
|
|
||||||
};
|
|
||||||
"/var/www/.well-known" = {
|
|
||||||
hostPath = "${cfg.storage}/challenge";
|
|
||||||
isReadOnly = false;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = { ... }: container.mkContainerConfig cfg {
|
|
||||||
environment.systemPackages = with pkgs; [
|
|
||||||
certbot
|
|
||||||
];
|
|
||||||
|
|
||||||
services.nginx = {
|
|
||||||
inherit virtualHosts;
|
|
||||||
enable = true;
|
|
||||||
clientMaxBodySize = "4096m";
|
|
||||||
recommendedOptimisation = true;
|
|
||||||
recommendedProxySettings = true;
|
|
||||||
appendConfig = util.trimTabs ''
|
|
||||||
worker_processes 4;
|
|
||||||
'';
|
|
||||||
eventsConfig = util.trimTabs ''
|
|
||||||
worker_connections 4096;
|
|
||||||
'';
|
|
||||||
appendHttpConfig = util.trimTabs ''
|
|
||||||
proxy_max_temp_file_size 0;
|
|
||||||
proxy_buffering off;
|
|
||||||
|
|
||||||
server {
|
|
||||||
listen 443 ssl default_server;
|
|
||||||
server_name _;
|
|
||||||
|
|
||||||
ssl_certificate /etc/letsencrypt/live/${config.container.domain}/fullchain.pem;
|
|
||||||
ssl_certificate_key /etc/letsencrypt/live/${config.container.domain}/privkey.pem;
|
|
||||||
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
|
||||||
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
|
||||||
|
|
||||||
return 403;
|
|
||||||
}
|
|
||||||
'';
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,53 +0,0 @@
|
||||||
{
|
|
||||||
config,
|
|
||||||
container,
|
|
||||||
lib,
|
|
||||||
pkgs,
|
|
||||||
util,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.rabbitmq;
|
|
||||||
in {
|
|
||||||
options.container.module.rabbitmq = {
|
|
||||||
enable = lib.mkEnableOption "the mqtt server.";
|
|
||||||
address = lib.mkOption {
|
|
||||||
default = "10.1.0.28";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
port = lib.mkOption {
|
|
||||||
default = 5672;
|
|
||||||
type = lib.types.int;
|
|
||||||
};
|
|
||||||
storage = lib.mkOption {
|
|
||||||
default = "${config.container.storage}/rabbitmq";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = lib.mkIf cfg.enable {
|
|
||||||
systemd.tmpfiles.rules = container.mkContainerDir cfg [
|
|
||||||
"data"
|
|
||||||
];
|
|
||||||
|
|
||||||
containers.rabbitmq = container.mkContainer cfg {
|
|
||||||
bindMounts = {
|
|
||||||
"/var/lib/rabbitmq" = {
|
|
||||||
hostPath = "${cfg.storage}/data";
|
|
||||||
isReadOnly = false;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = { ... }: container.mkContainerConfig cfg {
|
|
||||||
services.rabbitmq = {
|
|
||||||
enable = true;
|
|
||||||
dataDir = "/var/lib/rabbitmq";
|
|
||||||
listenAddress = cfg.address;
|
|
||||||
port = cfg.port;
|
|
||||||
configItems = {
|
|
||||||
"loopback_users" = "none";
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,59 +0,0 @@
|
||||||
{
|
|
||||||
config,
|
|
||||||
container,
|
|
||||||
lib,
|
|
||||||
pkgs,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.read;
|
|
||||||
in {
|
|
||||||
options.container.module.read = {
|
|
||||||
enable = lib.mkEnableOption "the reading server.";
|
|
||||||
address = lib.mkOption {
|
|
||||||
default = "10.1.0.39";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
port = lib.mkOption {
|
|
||||||
default = 5000;
|
|
||||||
type = lib.types.int;
|
|
||||||
};
|
|
||||||
domain = lib.mkOption {
|
|
||||||
default = "read.${config.container.domain}";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
storage = lib.mkOption {
|
|
||||||
default = "${config.container.storage}/read";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = lib.mkIf cfg.enable {
|
|
||||||
systemd.tmpfiles.rules = container.mkContainerDir cfg [
|
|
||||||
"data"
|
|
||||||
];
|
|
||||||
|
|
||||||
containers.read = container.mkContainer cfg {
|
|
||||||
bindMounts = {
|
|
||||||
"/var/lib/kavita" = {
|
|
||||||
hostPath = "${cfg.storage}/data";
|
|
||||||
isReadOnly = false;
|
|
||||||
};
|
|
||||||
}
|
|
||||||
// container.attachMedia "book" true
|
|
||||||
// container.attachMedia "manga" true
|
|
||||||
;
|
|
||||||
|
|
||||||
config = { ... }: container.mkContainerConfig cfg {
|
|
||||||
services.kavita = {
|
|
||||||
enable = true;
|
|
||||||
dataDir = "/var/lib/kavita";
|
|
||||||
tokenKeyFile = pkgs.writeText "KavitaToken" "xY19aQOa939/Ie6GCRGbubVK8zRwrgBY/20AuyMpYshUjwK1Uyl7bw1yknVh6jJIFIfwq2vAjeotOUq7NEsf9Q==";
|
|
||||||
settings = {
|
|
||||||
IpAddresses = cfg.address;
|
|
||||||
Port = cfg.port;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,35 +0,0 @@
|
||||||
{
|
|
||||||
config,
|
|
||||||
container,
|
|
||||||
lib,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.redis;
|
|
||||||
in {
|
|
||||||
options.container.module.redis = {
|
|
||||||
enable = lib.mkEnableOption "the Redis server.";
|
|
||||||
address = lib.mkOption {
|
|
||||||
default = "10.1.0.38";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
port = lib.mkOption {
|
|
||||||
default = 6379;
|
|
||||||
type = lib.types.int;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = lib.mkIf cfg.enable {
|
|
||||||
containers.redis = container.mkContainer cfg {
|
|
||||||
config = { ... }: container.mkContainerConfig cfg {
|
|
||||||
services.redis.servers.main = {
|
|
||||||
enable = true;
|
|
||||||
port = cfg.port;
|
|
||||||
bind = cfg.address;
|
|
||||||
extraParams = [
|
|
||||||
"--protected-mode no"
|
|
||||||
];
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,138 +0,0 @@
|
||||||
{
|
|
||||||
config,
|
|
||||||
container,
|
|
||||||
lib,
|
|
||||||
pkgs,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.search;
|
|
||||||
in {
|
|
||||||
options.container.module.search = {
|
|
||||||
enable = lib.mkEnableOption "the search frontend.";
|
|
||||||
address = lib.mkOption {
|
|
||||||
default = "10.1.0.26";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
port = lib.mkOption {
|
|
||||||
default = 8080;
|
|
||||||
type = lib.types.int;
|
|
||||||
};
|
|
||||||
domain = lib.mkOption {
|
|
||||||
default = "search.${config.container.domain}";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
storage = lib.mkOption {
|
|
||||||
default = "${config.container.storage}/search";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = lib.mkIf cfg.enable {
|
|
||||||
containers.search = container.mkContainer cfg {
|
|
||||||
config = { ... }: container.mkContainerConfig cfg {
|
|
||||||
services.searx = {
|
|
||||||
enable = true;
|
|
||||||
package = pkgs.searxng;
|
|
||||||
# REF: https://github.com/searxng/searxng/blob/master/searx/settings.yml
|
|
||||||
settings = {
|
|
||||||
general = {
|
|
||||||
debug = false;
|
|
||||||
enable_metrics = false;
|
|
||||||
instance_name = "SearX";
|
|
||||||
};
|
|
||||||
server = {
|
|
||||||
bind_address = cfg.address;
|
|
||||||
image_proxy = false;
|
|
||||||
limiter = false;
|
|
||||||
method = "GET";
|
|
||||||
port = cfg.port;
|
|
||||||
public_instance = false;
|
|
||||||
secret_key = "searxxx";
|
|
||||||
};
|
|
||||||
search = {
|
|
||||||
autocomplete = "";
|
|
||||||
autocomplete_min = 4;
|
|
||||||
default_lang = "auto";
|
|
||||||
safe_search = 0;
|
|
||||||
};
|
|
||||||
ui = {
|
|
||||||
center_alignment = false;
|
|
||||||
default_locale = "";
|
|
||||||
default_theme = "simple";
|
|
||||||
hotkeys = "vim";
|
|
||||||
infinite_scroll = false;
|
|
||||||
simple_style = "dark";
|
|
||||||
};
|
|
||||||
outgoing = {
|
|
||||||
enable_http2 = true;
|
|
||||||
max_request_timeout = 10.0;
|
|
||||||
pool_connections = 100;
|
|
||||||
pool_maxsize = 20;
|
|
||||||
request_timeout = 3.0;
|
|
||||||
# proxies = {
|
|
||||||
# "all://" = with config.container.module; [
|
|
||||||
# # "socks5:${frkn.address}:${frkn.port}"
|
|
||||||
# "socks5:${frkn.address}:1081"
|
|
||||||
# # "socks5:${frkn.address}:9150"
|
|
||||||
# ];
|
|
||||||
# };
|
|
||||||
# using_tor_proxy = true;
|
|
||||||
# extra_proxy_timeout = 10;
|
|
||||||
};
|
|
||||||
# plugins = [ ];
|
|
||||||
enabled_plugins = [
|
|
||||||
"Basic Calculator"
|
|
||||||
"Hostnames plugin"
|
|
||||||
"Tracker URL remover"
|
|
||||||
];
|
|
||||||
hostnames = {
|
|
||||||
replace = with config.container.module; {
|
|
||||||
"(.*\.)?youtu\.be$" = yt.domain;
|
|
||||||
"(.*\.)?youtube\.com$" = yt.domain;
|
|
||||||
};
|
|
||||||
remove = [
|
|
||||||
"(.*\.)?dzen\.ru$"
|
|
||||||
"(.*\.)?facebook.com$"
|
|
||||||
"(.*\.)?gosuslugi\.ru$"
|
|
||||||
"(.*\.)?quora\.com$"
|
|
||||||
"(.*\.)?rutube\.ru$"
|
|
||||||
"(.*\.)?vk\.com$"
|
|
||||||
];
|
|
||||||
low_priority = [
|
|
||||||
"(.*\.)?google(\..*)?$"
|
|
||||||
"(.*\.)?microsoft\.com$"
|
|
||||||
];
|
|
||||||
high_priority = [
|
|
||||||
"(.*\.)?4pda.to$"
|
|
||||||
"(.*\.)?github.com$"
|
|
||||||
"(.*\.)?wikipedia.org$"
|
|
||||||
];
|
|
||||||
};
|
|
||||||
categories_as_tabs = {
|
|
||||||
files = { };
|
|
||||||
general = { };
|
|
||||||
images = { };
|
|
||||||
it = { };
|
|
||||||
map = { };
|
|
||||||
news = { };
|
|
||||||
videos = { };
|
|
||||||
};
|
|
||||||
engines = let
|
|
||||||
mkEnable = name: {
|
|
||||||
inherit name;
|
|
||||||
disabled = false;
|
|
||||||
};
|
|
||||||
mkDisable = name: {
|
|
||||||
inherit name;
|
|
||||||
disabled = true;
|
|
||||||
};
|
|
||||||
in [
|
|
||||||
(mkEnable "bing")
|
|
||||||
(mkDisable "qwant")
|
|
||||||
];
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,66 +0,0 @@
|
||||||
{
|
|
||||||
config,
|
|
||||||
container,
|
|
||||||
lib,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.status;
|
|
||||||
in {
|
|
||||||
options.container.module.status = {
|
|
||||||
enable = lib.mkEnableOption "the status monitor.";
|
|
||||||
address = lib.mkOption {
|
|
||||||
default = "10.1.0.22";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
port = lib.mkOption {
|
|
||||||
default = 3001;
|
|
||||||
type = lib.types.int;
|
|
||||||
};
|
|
||||||
domain = lib.mkOption {
|
|
||||||
default = "status.${config.container.domain}";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
storage = lib.mkOption {
|
|
||||||
default = "${config.container.storage}/status";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = lib.mkIf cfg.enable {
|
|
||||||
systemd.tmpfiles.rules = container.mkContainerDir cfg [
|
|
||||||
"data"
|
|
||||||
];
|
|
||||||
|
|
||||||
containers.status = container.mkContainer cfg {
|
|
||||||
bindMounts = {
|
|
||||||
"/var/lib/uptime-kuma" = {
|
|
||||||
hostPath = "${cfg.storage}/data";
|
|
||||||
isReadOnly = false;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = { ... }: container.mkContainerConfig cfg {
|
|
||||||
networking = {
|
|
||||||
nameservers = lib.mkForce [
|
|
||||||
config.container.module.dns.address
|
|
||||||
];
|
|
||||||
};
|
|
||||||
|
|
||||||
services.uptime-kuma = {
|
|
||||||
enable = true;
|
|
||||||
settings = {
|
|
||||||
DATA_DIR = "/var/lib/uptime-kuma/";
|
|
||||||
HOST = cfg.address;
|
|
||||||
PORT = toString cfg.port;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
systemd.services.uptime-kuma = {
|
|
||||||
serviceConfig = {
|
|
||||||
DynamicUser = lib.mkForce false;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,62 +0,0 @@
|
||||||
{
|
|
||||||
config,
|
|
||||||
container,
|
|
||||||
lib,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.stock;
|
|
||||||
in {
|
|
||||||
options.container.module.stock = {
|
|
||||||
enable = lib.mkEnableOption "the stock management.";
|
|
||||||
address = lib.mkOption {
|
|
||||||
default = "10.1.0.45";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
port = lib.mkOption {
|
|
||||||
default = 80;
|
|
||||||
type = lib.types.int;
|
|
||||||
};
|
|
||||||
domain = lib.mkOption {
|
|
||||||
default = "stock.${config.container.domain}";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
storage = lib.mkOption {
|
|
||||||
default = "${config.container.storage}/stock";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = lib.mkIf cfg.enable {
|
|
||||||
systemd.tmpfiles.rules = container.mkContainerDir cfg [
|
|
||||||
"data"
|
|
||||||
];
|
|
||||||
|
|
||||||
containers.stock = container.mkContainer cfg {
|
|
||||||
bindMounts = {
|
|
||||||
"/var/lib/grocy" = {
|
|
||||||
hostPath = "${cfg.storage}/data";
|
|
||||||
isReadOnly = false;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = { ... }: container.mkContainerConfig cfg {
|
|
||||||
services.grocy = {
|
|
||||||
enable = true;
|
|
||||||
dataDir = "/var/lib/grocy";
|
|
||||||
hostName = cfg.domain;
|
|
||||||
nginx = {
|
|
||||||
enableSSL = false;
|
|
||||||
};
|
|
||||||
settings = {
|
|
||||||
calendar = {
|
|
||||||
firstDayOfWeek = 1;
|
|
||||||
showWeekNumber = true;
|
|
||||||
};
|
|
||||||
culture = "en";
|
|
||||||
currency = "RUB";
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,60 +0,0 @@
|
||||||
{
|
|
||||||
config,
|
|
||||||
container,
|
|
||||||
lib,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.terraria;
|
|
||||||
in {
|
|
||||||
options.container.module.terraria = {
|
|
||||||
enable = lib.mkEnableOption "the Terraria server.";
|
|
||||||
address = lib.mkOption {
|
|
||||||
default = "10.1.0.77";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
port = lib.mkOption {
|
|
||||||
default = 22777;
|
|
||||||
type = lib.types.int;
|
|
||||||
};
|
|
||||||
storage = lib.mkOption {
|
|
||||||
default = "${config.container.storage}/terraria";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = lib.mkIf cfg.enable {
|
|
||||||
systemd.tmpfiles.rules = container.mkContainerDir cfg [
|
|
||||||
"data"
|
|
||||||
];
|
|
||||||
|
|
||||||
containers.terraria = container.mkContainer cfg {
|
|
||||||
bindMounts = {
|
|
||||||
"/var/lib/terraria" = {
|
|
||||||
hostPath = "${cfg.storage}/data";
|
|
||||||
isReadOnly = false;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = { pkgs, ... }: container.mkContainerConfig cfg {
|
|
||||||
# NOTE: Admin with `tmux -S /var/lib/terraria/terraria.sock attach-session -t 0`
|
|
||||||
environment.systemPackages = with pkgs; [ tmux ];
|
|
||||||
|
|
||||||
services.terraria = let
|
|
||||||
dataDir = "/var/lib/terraria";
|
|
||||||
in {
|
|
||||||
inherit (cfg) port;
|
|
||||||
inherit dataDir;
|
|
||||||
enable = true;
|
|
||||||
autoCreatedWorldSize = "large";
|
|
||||||
maxPlayers = 4;
|
|
||||||
messageOfTheDay = "<3";
|
|
||||||
noUPnP = false;
|
|
||||||
openFirewall = false;
|
|
||||||
password = "mishadima143";
|
|
||||||
secure = false;
|
|
||||||
worldPath = "${dataDir}/.local/share/Terraria/Worlds/Together.wld";
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,122 +0,0 @@
|
||||||
# easyrsa --days=36500 init-pki
|
|
||||||
# easyrsa --days=36500 build-ca
|
|
||||||
# easyrsa --days=36500 build-server-full <SERVER_NAME> nopass
|
|
||||||
# easyrsa --days=36500 build-client-full <CLIENT_NAME> nopass
|
|
||||||
# easyrsa gen-crl
|
|
||||||
# openssl dhparam -out dh2048.pem 2048
|
|
||||||
# Don't forget to set tls hostname on the client to match SERVER_NAME *AND* disable ipv6 ?
|
|
||||||
|
|
||||||
# easyrsa revoke <CLIENT_NAME>
|
|
||||||
# easyrsa gen-crl
|
|
||||||
# restart container
|
|
||||||
|
|
||||||
# SEE: https://github.com/OpenVPN/openvpn/blob/master/sample/sample-config-files/server.conf
|
|
||||||
# SRC: https://github.com/TinCanTech/easy-tls
|
|
||||||
{
|
|
||||||
config,
|
|
||||||
container,
|
|
||||||
lib,
|
|
||||||
pkgs,
|
|
||||||
util,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.vpn;
|
|
||||||
in {
|
|
||||||
options.container.module.vpn = {
|
|
||||||
enable = lib.mkEnableOption "the vpn server.";
|
|
||||||
address = lib.mkOption {
|
|
||||||
default = "10.1.0.23";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
port = lib.mkOption {
|
|
||||||
default = 22145;
|
|
||||||
type = lib.types.int;
|
|
||||||
};
|
|
||||||
storage = lib.mkOption {
|
|
||||||
default = "${config.container.storage}/vpn";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
clients = lib.mkOption {
|
|
||||||
default = "10.1.1.0/24";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = lib.mkIf cfg.enable {
|
|
||||||
systemd.tmpfiles.rules = container.mkContainerDir cfg [
|
|
||||||
"data"
|
|
||||||
];
|
|
||||||
|
|
||||||
# HACK: I have no idea how to fully manage the container interface via networkd, so just add a route manually.
|
|
||||||
systemd.services.vpn-route = util.mkStaticSystemdService {
|
|
||||||
enable = true;
|
|
||||||
description = "Hack vpn routes on host";
|
|
||||||
after = [ "container@vpn.service" ];
|
|
||||||
wants = [ "container@vpn.service" ];
|
|
||||||
wantedBy = [ "multi-user.target" ];
|
|
||||||
serviceConfig = {
|
|
||||||
Type = "oneshot";
|
|
||||||
};
|
|
||||||
script = ''
|
|
||||||
${pkgs.iproute2}/bin/ip route add ${cfg.clients} via ${cfg.address} dev ve-vpn || true
|
|
||||||
'';
|
|
||||||
};
|
|
||||||
|
|
||||||
containers.vpn = container.mkContainer cfg {
|
|
||||||
bindMounts = {
|
|
||||||
"/data" = {
|
|
||||||
hostPath = "${cfg.storage}/data";
|
|
||||||
isReadOnly = true;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = { ... }: container.mkContainerConfig cfg {
|
|
||||||
boot.kernel.sysctl = {
|
|
||||||
"net.ipv4.conf.all.src_valid_mark" = 1;
|
|
||||||
"net.ipv4.ip_forward" = 1;
|
|
||||||
};
|
|
||||||
environment.systemPackages = with pkgs; [
|
|
||||||
easyrsa
|
|
||||||
openvpn
|
|
||||||
];
|
|
||||||
users = {
|
|
||||||
groups.openvpn = {};
|
|
||||||
users.openvpn = {
|
|
||||||
group = "openvpn";
|
|
||||||
isSystemUser = true;
|
|
||||||
uid = 1000;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
# NOTE: Change the `server` to match `cfg.clients` or write a substring here.
|
|
||||||
services.openvpn.servers.vpn = {
|
|
||||||
autoStart = true;
|
|
||||||
config = util.trimTabs ''
|
|
||||||
ca /data/pki/ca.crt
|
|
||||||
cert /data/pki/issued/home.crt
|
|
||||||
client-to-client
|
|
||||||
crl-verify /data/pki/crl.pem
|
|
||||||
dev tun
|
|
||||||
dh /data/dh2048.pem
|
|
||||||
explicit-exit-notify 1
|
|
||||||
group openvpn
|
|
||||||
ifconfig-pool-persist ipp.txt
|
|
||||||
keepalive 10 120
|
|
||||||
key /data/pki/private/home.key
|
|
||||||
persist-tun
|
|
||||||
port ${toString cfg.port}
|
|
||||||
proto udp
|
|
||||||
push "dhcp-option DNS 10.0.0.1"
|
|
||||||
push "dhcp-option DNS 10.0.0.1"
|
|
||||||
push "route 10.0.0.0 255.0.0.0"
|
|
||||||
push "route 192.168.1.0 255.255.255.0"
|
|
||||||
server 10.1.1.0 255.255.255.0
|
|
||||||
status openvpn-status.log
|
|
||||||
topology subnet
|
|
||||||
user openvpn
|
|
||||||
verb 4
|
|
||||||
'';
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,87 +0,0 @@
|
||||||
{
|
|
||||||
config,
|
|
||||||
container,
|
|
||||||
lib,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.watch;
|
|
||||||
in {
|
|
||||||
options.container.module.watch = {
|
|
||||||
enable = lib.mkEnableOption "the media server.";
|
|
||||||
address = lib.mkOption {
|
|
||||||
default = "10.1.0.11";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
port = lib.mkOption {
|
|
||||||
default = 8096;
|
|
||||||
type = lib.types.int;
|
|
||||||
};
|
|
||||||
domain = lib.mkOption {
|
|
||||||
default = "watch.${config.container.domain}";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
storage = lib.mkOption {
|
|
||||||
default = "${config.container.storage}/watch";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
memLimit = lib.mkOption {
|
|
||||||
default = "8G";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = lib.mkIf cfg.enable {
|
|
||||||
systemd.tmpfiles.rules = container.mkContainerDir cfg [
|
|
||||||
"cache"
|
|
||||||
"data"
|
|
||||||
];
|
|
||||||
|
|
||||||
containers.watch = container.mkContainer cfg {
|
|
||||||
bindMounts = {
|
|
||||||
"/var/lib/jellyfin" = {
|
|
||||||
hostPath = "${cfg.storage}/data";
|
|
||||||
isReadOnly = false;
|
|
||||||
};
|
|
||||||
"/var/cache/jellyfin" = {
|
|
||||||
hostPath = "${cfg.storage}/cache";
|
|
||||||
isReadOnly = false;
|
|
||||||
};
|
|
||||||
"/dev/dri" = {
|
|
||||||
hostPath = "/dev/dri";
|
|
||||||
isReadOnly = false;
|
|
||||||
};
|
|
||||||
}
|
|
||||||
// container.attachMedia "anime" true
|
|
||||||
// container.attachMedia "download" true
|
|
||||||
// container.attachMedia "movie" true
|
|
||||||
// container.attachMedia "music" true
|
|
||||||
// container.attachMedia "photo" true
|
|
||||||
// container.attachMedia "porn" true
|
|
||||||
// container.attachMedia "show" true
|
|
||||||
// container.attachMedia "study" true
|
|
||||||
// container.attachMedia "work" true
|
|
||||||
// container.attachMedia "youtube" true
|
|
||||||
;
|
|
||||||
|
|
||||||
allowedDevices = [
|
|
||||||
{
|
|
||||||
modifier = "rwm";
|
|
||||||
node = "/dev/dri/renderD128";
|
|
||||||
}
|
|
||||||
];
|
|
||||||
|
|
||||||
config = { ... }: container.mkContainerConfig cfg {
|
|
||||||
systemd.services.jellyfin.serviceConfig.MemoryLimit = cfg.memLimit;
|
|
||||||
services.jellyfin = {
|
|
||||||
enable = true;
|
|
||||||
cacheDir = "/var/cache/jellyfin";
|
|
||||||
dataDir = "/var/lib/jellyfin";
|
|
||||||
};
|
|
||||||
# users.users.jellyfin.extraGroups = [
|
|
||||||
# "video"
|
|
||||||
# "render"
|
|
||||||
# ];
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,65 +0,0 @@
|
||||||
{
|
|
||||||
__findFile,
|
|
||||||
config,
|
|
||||||
container,
|
|
||||||
inputs,
|
|
||||||
lib,
|
|
||||||
pkgs,
|
|
||||||
pkgsMaster,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.yt;
|
|
||||||
in {
|
|
||||||
options.container.module.yt = {
|
|
||||||
enable = lib.mkEnableOption "the YouTube frontend.";
|
|
||||||
address = lib.mkOption {
|
|
||||||
default = "10.1.0.19";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
port = lib.mkOption {
|
|
||||||
default = 3000;
|
|
||||||
type = lib.types.int;
|
|
||||||
};
|
|
||||||
domain = lib.mkOption {
|
|
||||||
default = "yt.${config.container.domain}";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
storage = lib.mkOption {
|
|
||||||
default = "${config.container.storage}/yt";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = lib.mkIf cfg.enable {
|
|
||||||
containers.yt = container.mkContainer cfg {
|
|
||||||
config = { ... }: container.mkContainerConfig cfg {
|
|
||||||
disabledModules = [ "services/web-apps/invidious.nix" ];
|
|
||||||
imports = [ "${inputs.nixpkgsMaster}/nixos/modules/services/web-apps/invidious.nix" ];
|
|
||||||
|
|
||||||
services.invidious = {
|
|
||||||
enable = true;
|
|
||||||
domain = cfg.domain;
|
|
||||||
package = pkgsMaster.invidious;
|
|
||||||
port = cfg.port;
|
|
||||||
nginx.enable = false;
|
|
||||||
database = {
|
|
||||||
host = config.container.module.postgres.address;
|
|
||||||
port = config.container.module.postgres.port;
|
|
||||||
createLocally = false;
|
|
||||||
passwordFile = "${pkgs.writeText "InvidiousDbPassword" "invidious"}";
|
|
||||||
};
|
|
||||||
settings = {
|
|
||||||
captcha_enabled = false;
|
|
||||||
check_tables = true;
|
|
||||||
external_port = 443;
|
|
||||||
https_only = true;
|
|
||||||
registration_enabled = false;
|
|
||||||
admins = [
|
|
||||||
"root"
|
|
||||||
];
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,57 +0,0 @@
|
||||||
{
|
|
||||||
config,
|
|
||||||
lib,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container;
|
|
||||||
in {
|
|
||||||
options.container = {
|
|
||||||
enable = lib.mkEnableOption "Containers!!";
|
|
||||||
autoStart = lib.mkOption {
|
|
||||||
default = false;
|
|
||||||
type = lib.types.bool;
|
|
||||||
};
|
|
||||||
host = lib.mkOption {
|
|
||||||
default = "0.0.0.0";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
localAccess = lib.mkOption {
|
|
||||||
default = "0.0.0.0";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
storage = lib.mkOption {
|
|
||||||
default = "/tmp/container";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
domain = lib.mkOption {
|
|
||||||
default = "local";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
interface = lib.mkOption {
|
|
||||||
default = "lo";
|
|
||||||
type = lib.types.str;
|
|
||||||
};
|
|
||||||
media = lib.mkOption {
|
|
||||||
default = { };
|
|
||||||
type = lib.types.attrs;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config = lib.mkIf cfg.enable {
|
|
||||||
# This is the network for all the containers.
|
|
||||||
# They are not available to the external interface by default,
|
|
||||||
# instead they all expose specific ports in their configuration.
|
|
||||||
networking = {
|
|
||||||
nat = {
|
|
||||||
enable = true;
|
|
||||||
externalInterface = config.container.interface;
|
|
||||||
internalInterfaces = [
|
|
||||||
"ve-+"
|
|
||||||
];
|
|
||||||
};
|
|
||||||
networkmanager.unmanaged = [
|
|
||||||
"interface-name:ve-*"
|
|
||||||
];
|
|
||||||
};
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,30 +0,0 @@
|
||||||
{
|
|
||||||
config,
|
|
||||||
container,
|
|
||||||
util,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
address = "192.168.2.249";
|
|
||||||
domain = "camera.${config.container.domain}";
|
|
||||||
port = 554;
|
|
||||||
in {
|
|
||||||
${domain} = container.mkServer {
|
|
||||||
extraConfig = util.trimTabs ''
|
|
||||||
listen 443 ssl;
|
|
||||||
|
|
||||||
location / {
|
|
||||||
allow ${config.container.localAccess};
|
|
||||||
allow ${config.container.module.status.address};
|
|
||||||
allow ${config.container.module.vpn.clients};
|
|
||||||
allow ${config.container.module.frkn.address};
|
|
||||||
deny all;
|
|
||||||
return 301 rtsp://${address}:${toString port}/live/main;
|
|
||||||
}
|
|
||||||
|
|
||||||
ssl_certificate /etc/letsencrypt/live/${config.container.domain}/fullchain.pem;
|
|
||||||
ssl_certificate_key /etc/letsencrypt/live/${config.container.domain}/privkey.pem;
|
|
||||||
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
|
||||||
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
|
||||||
'';
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,33 +0,0 @@
|
||||||
{
|
|
||||||
config,
|
|
||||||
container,
|
|
||||||
util,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.change;
|
|
||||||
name = "change";
|
|
||||||
in {
|
|
||||||
${cfg.domain} = container.mkServer {
|
|
||||||
extraConfig = util.trimTabs ''
|
|
||||||
listen 443 ssl;
|
|
||||||
set ''$${name} ${cfg.address}:${toString cfg.port};
|
|
||||||
|
|
||||||
location / {
|
|
||||||
allow ${config.container.localAccess};
|
|
||||||
allow ${config.container.module.status.address};
|
|
||||||
allow ${config.container.module.vpn.clients};
|
|
||||||
allow ${config.container.module.frkn.address};
|
|
||||||
deny all;
|
|
||||||
|
|
||||||
proxy_pass http://''$${name}$request_uri;
|
|
||||||
|
|
||||||
add_header Referrer-Policy 'origin';
|
|
||||||
}
|
|
||||||
|
|
||||||
ssl_certificate /etc/letsencrypt/live/${config.container.domain}/fullchain.pem;
|
|
||||||
ssl_certificate_key /etc/letsencrypt/live/${config.container.domain}/privkey.pem;
|
|
||||||
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
|
||||||
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
|
||||||
'';
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,31 +0,0 @@
|
||||||
{
|
|
||||||
config,
|
|
||||||
container,
|
|
||||||
util,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.chat;
|
|
||||||
name = "chat";
|
|
||||||
in {
|
|
||||||
${cfg.domain} = container.mkServer {
|
|
||||||
extraConfig = util.trimTabs ''
|
|
||||||
listen 443 ssl;
|
|
||||||
set ''$${name} ${cfg.address}:${toString cfg.port};
|
|
||||||
|
|
||||||
location / {
|
|
||||||
allow ${config.container.localAccess};
|
|
||||||
allow ${config.container.module.status.address};
|
|
||||||
allow ${config.container.module.vpn.clients};
|
|
||||||
allow ${config.container.module.frkn.address};
|
|
||||||
deny all;
|
|
||||||
|
|
||||||
proxy_pass http://''$${name}$request_uri;
|
|
||||||
}
|
|
||||||
|
|
||||||
ssl_certificate /etc/letsencrypt/live/${config.container.domain}/fullchain.pem;
|
|
||||||
ssl_certificate_key /etc/letsencrypt/live/${config.container.domain}/privkey.pem;
|
|
||||||
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
|
||||||
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
|
||||||
'';
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,34 +0,0 @@
|
||||||
{
|
|
||||||
config,
|
|
||||||
container,
|
|
||||||
util,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.cloud;
|
|
||||||
name = "cloud";
|
|
||||||
in {
|
|
||||||
${cfg.domain} = container.mkServer {
|
|
||||||
extraConfig = util.trimTabs ''
|
|
||||||
listen 443 ssl;
|
|
||||||
set ''$${name} ${cfg.address}:${toString cfg.port};
|
|
||||||
|
|
||||||
location ~ ^/(settings/admin|settings/users|settings/apps|login|api) {
|
|
||||||
allow ${config.container.localAccess};
|
|
||||||
allow ${config.container.module.status.address};
|
|
||||||
allow ${config.container.module.vpn.clients};
|
|
||||||
allow ${config.container.module.frkn.address};
|
|
||||||
deny all;
|
|
||||||
proxy_pass http://''$${name}$request_uri;
|
|
||||||
}
|
|
||||||
|
|
||||||
location / {
|
|
||||||
proxy_pass http://''$${name}$request_uri;
|
|
||||||
}
|
|
||||||
|
|
||||||
ssl_certificate /etc/letsencrypt/live/${config.container.domain}/fullchain.pem;
|
|
||||||
ssl_certificate_key /etc/letsencrypt/live/${config.container.domain}/privkey.pem;
|
|
||||||
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
|
||||||
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
|
||||||
'';
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,30 +0,0 @@
|
||||||
{
|
|
||||||
config,
|
|
||||||
container,
|
|
||||||
util,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.download;
|
|
||||||
name = "download";
|
|
||||||
in {
|
|
||||||
${cfg.domain} = container.mkServer {
|
|
||||||
extraConfig = util.trimTabs ''
|
|
||||||
listen 443 ssl;
|
|
||||||
set ''$${name} ${cfg.address}:${toString cfg.port};
|
|
||||||
|
|
||||||
location / {
|
|
||||||
allow ${config.container.localAccess};
|
|
||||||
allow ${config.container.module.status.address};
|
|
||||||
allow ${config.container.module.vpn.clients};
|
|
||||||
allow ${config.container.module.frkn.address};
|
|
||||||
deny all;
|
|
||||||
proxy_pass http://''$${name}$request_uri;
|
|
||||||
}
|
|
||||||
|
|
||||||
ssl_certificate /etc/letsencrypt/live/${config.container.domain}/fullchain.pem;
|
|
||||||
ssl_certificate_key /etc/letsencrypt/live/${config.container.domain}/privkey.pem;
|
|
||||||
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
|
||||||
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
|
||||||
'';
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,33 +0,0 @@
|
||||||
{
|
|
||||||
container,
|
|
||||||
config,
|
|
||||||
util,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.git;
|
|
||||||
name = "git";
|
|
||||||
in {
|
|
||||||
${cfg.domain} = container.mkServer {
|
|
||||||
extraConfig = util.trimTabs ''
|
|
||||||
listen 443 ssl;
|
|
||||||
set ''$${name} ${cfg.address}:${toString cfg.port};
|
|
||||||
|
|
||||||
location ~ ^/(admin|api|user) {
|
|
||||||
allow ${config.container.localAccess};
|
|
||||||
allow ${config.container.module.vpn.clients};
|
|
||||||
allow ${config.container.module.frkn.address};
|
|
||||||
deny all;
|
|
||||||
proxy_pass http://''$${name}$request_uri;
|
|
||||||
}
|
|
||||||
|
|
||||||
location / {
|
|
||||||
proxy_pass http://''$${name}$request_uri;
|
|
||||||
}
|
|
||||||
|
|
||||||
ssl_certificate /etc/letsencrypt/live/${config.container.domain}/fullchain.pem;
|
|
||||||
ssl_certificate_key /etc/letsencrypt/live/${config.container.domain}/privkey.pem;
|
|
||||||
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
|
||||||
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
|
||||||
'';
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,30 +0,0 @@
|
||||||
{
|
|
||||||
config,
|
|
||||||
container,
|
|
||||||
util,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.home;
|
|
||||||
name = "home";
|
|
||||||
in {
|
|
||||||
${cfg.domain} = container.mkServer {
|
|
||||||
extraConfig = util.trimTabs ''
|
|
||||||
listen 443 ssl;
|
|
||||||
set ''$${name} ${cfg.address}:${toString cfg.port};
|
|
||||||
|
|
||||||
location / {
|
|
||||||
allow ${config.container.localAccess};
|
|
||||||
allow ${config.container.module.status.address};
|
|
||||||
allow ${config.container.module.vpn.clients};
|
|
||||||
allow ${config.container.module.frkn.address};
|
|
||||||
deny all;
|
|
||||||
proxy_pass http://''$${name}$request_uri;
|
|
||||||
}
|
|
||||||
|
|
||||||
ssl_certificate /etc/letsencrypt/live/${config.container.domain}/fullchain.pem;
|
|
||||||
ssl_certificate_key /etc/letsencrypt/live/${config.container.domain}/privkey.pem;
|
|
||||||
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
|
||||||
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
|
||||||
'';
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,37 +0,0 @@
|
||||||
{
|
|
||||||
container,
|
|
||||||
config,
|
|
||||||
util,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.iot;
|
|
||||||
name = "iot";
|
|
||||||
in {
|
|
||||||
${cfg.domain} = container.mkServer {
|
|
||||||
extraConfig = util.trimTabs ''
|
|
||||||
listen 443 ssl;
|
|
||||||
set ''$${name} ${cfg.address}:${toString cfg.port};
|
|
||||||
|
|
||||||
location / {
|
|
||||||
allow ${config.container.localAccess};
|
|
||||||
allow ${config.container.module.status.address};
|
|
||||||
allow ${config.container.module.vpn.clients};
|
|
||||||
allow ${config.container.module.frkn.address};
|
|
||||||
deny all;
|
|
||||||
|
|
||||||
# proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
|
|
||||||
proxy_set_header Host $host;
|
|
||||||
proxy_http_version 1.1;
|
|
||||||
proxy_set_header Upgrade $http_upgrade;
|
|
||||||
proxy_set_header Connection "upgrade";
|
|
||||||
|
|
||||||
proxy_pass http://''$${name}$request_uri;
|
|
||||||
}
|
|
||||||
|
|
||||||
ssl_certificate /etc/letsencrypt/live/${config.container.domain}/fullchain.pem;
|
|
||||||
ssl_certificate_key /etc/letsencrypt/live/${config.container.domain}/privkey.pem;
|
|
||||||
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
|
||||||
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
|
||||||
'';
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,30 +0,0 @@
|
||||||
{
|
|
||||||
container,
|
|
||||||
config,
|
|
||||||
util,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.mail;
|
|
||||||
name = "mail";
|
|
||||||
in {
|
|
||||||
${cfg.domain} = container.mkServer {
|
|
||||||
extraConfig = util.trimTabs ''
|
|
||||||
listen 443 ssl;
|
|
||||||
set ''$${name} ${cfg.address}:${toString cfg.port};
|
|
||||||
|
|
||||||
location / {
|
|
||||||
allow ${config.container.localAccess};
|
|
||||||
allow ${config.container.module.status.address};
|
|
||||||
allow ${config.container.module.vpn.clients};
|
|
||||||
allow ${config.container.module.frkn.address};
|
|
||||||
deny all;
|
|
||||||
proxy_pass http://''$${name}$request_uri;
|
|
||||||
}
|
|
||||||
|
|
||||||
ssl_certificate /etc/letsencrypt/live/${config.container.domain}/fullchain.pem;
|
|
||||||
ssl_certificate_key /etc/letsencrypt/live/${config.container.domain}/privkey.pem;
|
|
||||||
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
|
||||||
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
|
||||||
'';
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,31 +0,0 @@
|
||||||
{
|
|
||||||
container,
|
|
||||||
config,
|
|
||||||
util,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.office;
|
|
||||||
name = "office";
|
|
||||||
in {
|
|
||||||
${cfg.domain} = container.mkServer {
|
|
||||||
extraConfig = util.trimTabs ''
|
|
||||||
listen 443 ssl;
|
|
||||||
set ''$${name} ${cfg.address}:${toString cfg.port};
|
|
||||||
|
|
||||||
location / {
|
|
||||||
# allow ${config.container.localAccess};
|
|
||||||
# allow ${config.container.module.status.address};
|
|
||||||
# allow ${config.container.module.vpn.clients};
|
|
||||||
# allow ${config.container.module.frkn.address};
|
|
||||||
# deny all;
|
|
||||||
add_header X-Forwarded-Proto https;
|
|
||||||
proxy_pass http://''$${name}$request_uri;
|
|
||||||
}
|
|
||||||
|
|
||||||
ssl_certificate /etc/letsencrypt/live/${config.container.domain}/fullchain.pem;
|
|
||||||
ssl_certificate_key /etc/letsencrypt/live/${config.container.domain}/privkey.pem;
|
|
||||||
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
|
||||||
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
|
||||||
'';
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,30 +0,0 @@
|
||||||
{
|
|
||||||
container,
|
|
||||||
config,
|
|
||||||
util,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.paper;
|
|
||||||
name = "paper";
|
|
||||||
in {
|
|
||||||
${cfg.domain} = container.mkServer {
|
|
||||||
extraConfig = util.trimTabs ''
|
|
||||||
listen 443 ssl;
|
|
||||||
set ''$${name} ${cfg.address}:${toString cfg.port};
|
|
||||||
|
|
||||||
location / {
|
|
||||||
allow ${config.container.localAccess};
|
|
||||||
allow ${config.container.module.status.address};
|
|
||||||
allow ${config.container.module.vpn.clients};
|
|
||||||
allow ${config.container.module.frkn.address};
|
|
||||||
deny all;
|
|
||||||
proxy_pass http://''$${name}$request_uri;
|
|
||||||
}
|
|
||||||
|
|
||||||
ssl_certificate /etc/letsencrypt/live/${config.container.domain}/fullchain.pem;
|
|
||||||
ssl_certificate_key /etc/letsencrypt/live/${config.container.domain}/privkey.pem;
|
|
||||||
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
|
||||||
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
|
||||||
'';
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,30 +0,0 @@
|
||||||
{
|
|
||||||
container,
|
|
||||||
config,
|
|
||||||
util,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.pass;
|
|
||||||
name = "pass";
|
|
||||||
in {
|
|
||||||
${cfg.domain} = container.mkServer {
|
|
||||||
extraConfig = util.trimTabs ''
|
|
||||||
listen 443 ssl;
|
|
||||||
set ''$${name} ${cfg.address}:${toString cfg.port};
|
|
||||||
|
|
||||||
location / {
|
|
||||||
allow ${config.container.localAccess};
|
|
||||||
allow ${config.container.module.status.address};
|
|
||||||
allow ${config.container.module.vpn.clients};
|
|
||||||
allow ${config.container.module.frkn.address};
|
|
||||||
deny all;
|
|
||||||
proxy_pass http://''$${name}$request_uri;
|
|
||||||
}
|
|
||||||
|
|
||||||
ssl_certificate /etc/letsencrypt/live/${config.container.domain}/fullchain.pem;
|
|
||||||
ssl_certificate_key /etc/letsencrypt/live/${config.container.domain}/privkey.pem;
|
|
||||||
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
|
||||||
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
|
||||||
'';
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,29 +0,0 @@
|
||||||
{
|
|
||||||
container,
|
|
||||||
config,
|
|
||||||
util,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.paste;
|
|
||||||
name = "paste";
|
|
||||||
in {
|
|
||||||
${cfg.domain} = container.mkServer {
|
|
||||||
extraConfig = util.trimTabs ''
|
|
||||||
listen 443 ssl;
|
|
||||||
set ''$${name} ${cfg.address}:${toString cfg.port};
|
|
||||||
|
|
||||||
location = / {
|
|
||||||
return 403;
|
|
||||||
}
|
|
||||||
|
|
||||||
location / {
|
|
||||||
proxy_pass http://''$${name}$request_uri;
|
|
||||||
}
|
|
||||||
|
|
||||||
ssl_certificate /etc/letsencrypt/live/${config.container.domain}/fullchain.pem;
|
|
||||||
ssl_certificate_key /etc/letsencrypt/live/${config.container.domain}/privkey.pem;
|
|
||||||
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
|
||||||
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
|
||||||
'';
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,35 +0,0 @@
|
||||||
{
|
|
||||||
container,
|
|
||||||
config,
|
|
||||||
util,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.print;
|
|
||||||
name = "print";
|
|
||||||
in {
|
|
||||||
${cfg.domain} = container.mkServer {
|
|
||||||
extraConfig = util.trimTabs ''
|
|
||||||
listen 443 ssl;
|
|
||||||
set ''$${name} ${cfg.address}:${toString cfg.port};
|
|
||||||
|
|
||||||
location / {
|
|
||||||
allow ${config.container.localAccess};
|
|
||||||
allow ${config.container.module.status.address};
|
|
||||||
allow ${config.container.module.vpn.clients};
|
|
||||||
allow ${config.container.module.frkn.address};
|
|
||||||
deny all;
|
|
||||||
|
|
||||||
proxy_pass http://''$${name}$request_uri;
|
|
||||||
|
|
||||||
proxy_set_header Host "127.0.0.1";
|
|
||||||
proxy_set_header X-Real-IP $remote_addr;
|
|
||||||
proxy_set_header X-Forward-For $proxy_add_x_forwarded_for;
|
|
||||||
}
|
|
||||||
|
|
||||||
ssl_certificate /etc/letsencrypt/live/${config.container.domain}/fullchain.pem;
|
|
||||||
ssl_certificate_key /etc/letsencrypt/live/${config.container.domain}/privkey.pem;
|
|
||||||
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
|
||||||
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
|
||||||
'';
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,32 +0,0 @@
|
||||||
{
|
|
||||||
container,
|
|
||||||
config,
|
|
||||||
util,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
address = "192.168.2.237";
|
|
||||||
domain = "printer.${config.container.domain}";
|
|
||||||
name = "printer";
|
|
||||||
port = 80;
|
|
||||||
in {
|
|
||||||
${domain} = container.mkServer {
|
|
||||||
extraConfig = util.trimTabs ''
|
|
||||||
listen 443 ssl;
|
|
||||||
set ''$${name} ${address}:${toString port};
|
|
||||||
|
|
||||||
location / {
|
|
||||||
allow ${config.container.localAccess};
|
|
||||||
allow ${config.container.module.status.address};
|
|
||||||
allow ${config.container.module.vpn.clients};
|
|
||||||
allow ${config.container.module.frkn.address};
|
|
||||||
deny all;
|
|
||||||
proxy_pass http://''$${name}$request_uri;
|
|
||||||
}
|
|
||||||
|
|
||||||
ssl_certificate /etc/letsencrypt/live/${config.container.domain}/fullchain.pem;
|
|
||||||
ssl_certificate_key /etc/letsencrypt/live/${config.container.domain}/privkey.pem;
|
|
||||||
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
|
||||||
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
|
||||||
'';
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,30 +0,0 @@
|
||||||
{
|
|
||||||
container,
|
|
||||||
config,
|
|
||||||
util,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.read;
|
|
||||||
name = "read";
|
|
||||||
in {
|
|
||||||
${cfg.domain} = container.mkServer {
|
|
||||||
extraConfig = util.trimTabs ''
|
|
||||||
listen 443 ssl;
|
|
||||||
set ''$${name} ${cfg.address}:${toString cfg.port};
|
|
||||||
|
|
||||||
location / {
|
|
||||||
allow ${config.container.localAccess};
|
|
||||||
allow ${config.container.module.status.address};
|
|
||||||
allow ${config.container.module.vpn.clients};
|
|
||||||
allow ${config.container.module.frkn.address};
|
|
||||||
deny all;
|
|
||||||
proxy_pass http://''$${name}$request_uri;
|
|
||||||
}
|
|
||||||
|
|
||||||
ssl_certificate /etc/letsencrypt/live/${config.container.domain}/fullchain.pem;
|
|
||||||
ssl_certificate_key /etc/letsencrypt/live/${config.container.domain}/privkey.pem;
|
|
||||||
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
|
||||||
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
|
||||||
'';
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,26 +0,0 @@
|
||||||
{
|
|
||||||
container,
|
|
||||||
config,
|
|
||||||
util,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
domain = "resume.${config.container.domain}";
|
|
||||||
in {
|
|
||||||
${domain} = container.mkServer {
|
|
||||||
extraConfig = util.trimTabs ''
|
|
||||||
server_name ${domain};
|
|
||||||
listen 443 ssl;
|
|
||||||
|
|
||||||
ssl_certificate /etc/letsencrypt/live/${config.container.domain}/fullchain.pem;
|
|
||||||
ssl_certificate_key /etc/letsencrypt/live/${config.container.domain}/privkey.pem;
|
|
||||||
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
|
||||||
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
|
||||||
|
|
||||||
if ($http_accept_language ~ ru) {
|
|
||||||
return 301 https://${config.container.module.git.domain}/voronind/resume/releases/download/latest/VoronindRu.pdf;
|
|
||||||
}
|
|
||||||
|
|
||||||
return 301 https://${config.container.module.git.domain}/voronind/resume/releases/download/latest/VoronindEn.pdf;
|
|
||||||
'';
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,32 +0,0 @@
|
||||||
{
|
|
||||||
container,
|
|
||||||
config,
|
|
||||||
util,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
address = "10.0.0.2";
|
|
||||||
domain = "router.${config.container.domain}";
|
|
||||||
name = "router";
|
|
||||||
port = 80;
|
|
||||||
in {
|
|
||||||
${domain} = container.mkServer {
|
|
||||||
extraConfig = util.trimTabs ''
|
|
||||||
listen 443 ssl;
|
|
||||||
set ''$${name} ${address}:${toString port};
|
|
||||||
|
|
||||||
location / {
|
|
||||||
allow ${config.container.localAccess};
|
|
||||||
allow ${config.container.module.status.address};
|
|
||||||
allow ${config.container.module.vpn.clients};
|
|
||||||
allow ${config.container.module.frkn.address};
|
|
||||||
deny all;
|
|
||||||
proxy_pass http://''$${name}$request_uri;
|
|
||||||
}
|
|
||||||
|
|
||||||
ssl_certificate /etc/letsencrypt/live/${config.container.domain}/fullchain.pem;
|
|
||||||
ssl_certificate_key /etc/letsencrypt/live/${config.container.domain}/privkey.pem;
|
|
||||||
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
|
||||||
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
|
||||||
'';
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,30 +0,0 @@
|
||||||
{
|
|
||||||
container,
|
|
||||||
config,
|
|
||||||
util,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.search;
|
|
||||||
name = "search";
|
|
||||||
in {
|
|
||||||
${cfg.domain} = container.mkServer {
|
|
||||||
extraConfig = util.trimTabs ''
|
|
||||||
listen 443 ssl;
|
|
||||||
set ''$${name} ${cfg.address}:${toString cfg.port};
|
|
||||||
|
|
||||||
location / {
|
|
||||||
allow ${config.container.localAccess};
|
|
||||||
allow ${config.container.module.status.address};
|
|
||||||
allow ${config.container.module.vpn.clients};
|
|
||||||
allow ${config.container.module.frkn.address};
|
|
||||||
deny all;
|
|
||||||
proxy_pass http://''$${name}$request_uri;
|
|
||||||
}
|
|
||||||
|
|
||||||
ssl_certificate /etc/letsencrypt/live/${config.container.domain}/fullchain.pem;
|
|
||||||
ssl_certificate_key /etc/letsencrypt/live/${config.container.domain}/privkey.pem;
|
|
||||||
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
|
||||||
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
|
||||||
'';
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,37 +0,0 @@
|
||||||
{
|
|
||||||
container,
|
|
||||||
config,
|
|
||||||
util,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.status;
|
|
||||||
name = "sstatus";
|
|
||||||
in {
|
|
||||||
${cfg.domain} = container.mkServer {
|
|
||||||
extraConfig = util.trimTabs ''
|
|
||||||
listen 443 ssl;
|
|
||||||
set ''$${name} ${cfg.address}:${toString cfg.port};
|
|
||||||
|
|
||||||
location ~ ^/(dashboard|settings) {
|
|
||||||
allow ${config.container.localAccess};
|
|
||||||
allow ${config.container.module.vpn.clients};
|
|
||||||
allow ${config.container.module.frkn.address};
|
|
||||||
deny all;
|
|
||||||
proxy_pass http://''$${name}$request_uri;
|
|
||||||
}
|
|
||||||
|
|
||||||
location / {
|
|
||||||
allow ${config.container.localAccess};
|
|
||||||
allow ${config.container.module.vpn.clients};
|
|
||||||
allow ${config.container.module.frkn.address};
|
|
||||||
deny all;
|
|
||||||
proxy_pass http://''$${name}$request_uri;
|
|
||||||
}
|
|
||||||
|
|
||||||
ssl_certificate /etc/letsencrypt/live/${config.container.domain}/fullchain.pem;
|
|
||||||
ssl_certificate_key /etc/letsencrypt/live/${config.container.domain}/privkey.pem;
|
|
||||||
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
|
||||||
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
|
||||||
'';
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,30 +0,0 @@
|
||||||
{
|
|
||||||
container,
|
|
||||||
config,
|
|
||||||
util,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.stock;
|
|
||||||
name = "stock";
|
|
||||||
in {
|
|
||||||
${cfg.domain} = container.mkServer {
|
|
||||||
extraConfig = util.trimTabs ''
|
|
||||||
listen 443 ssl;
|
|
||||||
set ''$${name} ${cfg.address}:${toString cfg.port};
|
|
||||||
|
|
||||||
location / {
|
|
||||||
allow ${config.container.localAccess};
|
|
||||||
allow ${config.container.module.status.address};
|
|
||||||
allow ${config.container.module.vpn.clients};
|
|
||||||
allow ${config.container.module.frkn.address};
|
|
||||||
deny all;
|
|
||||||
proxy_pass http://''$${name}$request_uri;
|
|
||||||
}
|
|
||||||
|
|
||||||
ssl_certificate /etc/letsencrypt/live/${config.container.domain}/fullchain.pem;
|
|
||||||
ssl_certificate_key /etc/letsencrypt/live/${config.container.domain}/privkey.pem;
|
|
||||||
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
|
||||||
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
|
||||||
'';
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,30 +0,0 @@
|
||||||
{
|
|
||||||
container,
|
|
||||||
config,
|
|
||||||
util,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.watch;
|
|
||||||
name = "watch";
|
|
||||||
in {
|
|
||||||
${cfg.domain} = container.mkServer {
|
|
||||||
extraConfig = util.trimTabs ''
|
|
||||||
listen 443 ssl;
|
|
||||||
set ''$${name} ${cfg.address}:${toString cfg.port};
|
|
||||||
|
|
||||||
location / {
|
|
||||||
allow ${config.container.localAccess};
|
|
||||||
allow ${config.container.module.status.address};
|
|
||||||
allow ${config.container.module.vpn.clients};
|
|
||||||
allow ${config.container.module.frkn.address};
|
|
||||||
deny all;
|
|
||||||
proxy_pass http://''$${name}$request_uri;
|
|
||||||
}
|
|
||||||
|
|
||||||
ssl_certificate /etc/letsencrypt/live/${config.container.domain}/fullchain.pem;
|
|
||||||
ssl_certificate_key /etc/letsencrypt/live/${config.container.domain}/privkey.pem;
|
|
||||||
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
|
||||||
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
|
||||||
'';
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -1,40 +0,0 @@
|
||||||
{
|
|
||||||
container,
|
|
||||||
config,
|
|
||||||
util,
|
|
||||||
...
|
|
||||||
}: let
|
|
||||||
cfg = config.container.module.yt;
|
|
||||||
name = "yt";
|
|
||||||
in {
|
|
||||||
${cfg.domain} = container.mkServer {
|
|
||||||
extraConfig = util.trimTabs ''
|
|
||||||
listen 443 ssl;
|
|
||||||
set ''$${name} ${cfg.address}:${toString cfg.port};
|
|
||||||
|
|
||||||
location / {
|
|
||||||
allow ${config.container.localAccess};
|
|
||||||
allow ${config.container.module.status.address};
|
|
||||||
allow ${config.container.module.vpn.clients};
|
|
||||||
allow ${config.container.module.frkn.address};
|
|
||||||
deny all;
|
|
||||||
|
|
||||||
proxy_pass http://''$${name}$request_uri;
|
|
||||||
|
|
||||||
proxy_set_header X-Forwarded-For $remote_addr;
|
|
||||||
proxy_set_header Host $host;
|
|
||||||
proxy_http_version 1.1;
|
|
||||||
proxy_set_header Connection "";
|
|
||||||
|
|
||||||
proxy_hide_header Content-Security-Policy;
|
|
||||||
proxy_hide_header X-Frame-Options;
|
|
||||||
proxy_hide_header X-Content-Type-Options;
|
|
||||||
}
|
|
||||||
|
|
||||||
ssl_certificate /etc/letsencrypt/live/${config.container.domain}/fullchain.pem;
|
|
||||||
ssl_certificate_key /etc/letsencrypt/live/${config.container.domain}/privkey.pem;
|
|
||||||
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
|
||||||
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
|
||||||
'';
|
|
||||||
};
|
|
||||||
}
|
|
|
@ -120,7 +120,6 @@
|
||||||
# HM config.
|
# HM config.
|
||||||
./home/NixOs.nix
|
./home/NixOs.nix
|
||||||
]
|
]
|
||||||
++ (self.ls ./container)
|
|
||||||
++ (self.ls ./host/${system}/${hostname})
|
++ (self.ls ./host/${system}/${hostname})
|
||||||
++ (self.ls ./option)
|
++ (self.ls ./option)
|
||||||
++ (self.ls ./config)
|
++ (self.ls ./config)
|
||||||
|
@ -128,14 +127,11 @@
|
||||||
++ (self.ls ./system)
|
++ (self.ls ./system)
|
||||||
;
|
;
|
||||||
specialArgs = let
|
specialArgs = let
|
||||||
pkgs = nixpkgs.legacyPackages.${system}.pkgs;
|
|
||||||
lib = nixpkgs.lib;
|
lib = nixpkgs.lib;
|
||||||
config = self.nixosConfigurations.${hostname}.config;
|
|
||||||
util = import ./lib/Util.nix { inherit lib; };
|
util = import ./lib/Util.nix { inherit lib; };
|
||||||
in {
|
in {
|
||||||
inherit (self) const __findFile;
|
inherit (self) const __findFile;
|
||||||
inherit inputs self poetry2nixJobber util;
|
inherit inputs self poetry2nixJobber util;
|
||||||
container = import ./lib/Container.nix { inherit lib pkgs config util; inherit (self) const; };
|
|
||||||
pkgsJobber = nixpkgsJobber.legacyPackages.${system}.pkgs;
|
pkgsJobber = nixpkgsJobber.legacyPackages.${system}.pkgs;
|
||||||
pkgsMaster = nixpkgsMaster.legacyPackages.${system}.pkgs;
|
pkgsMaster = nixpkgsMaster.legacyPackages.${system}.pkgs;
|
||||||
pkgsUnstable = nixpkgsUnstable.legacyPackages.${system}.pkgs;
|
pkgsUnstable = nixpkgsUnstable.legacyPackages.${system}.pkgs;
|
||||||
|
|
|
@ -17,7 +17,7 @@
|
||||||
path_src="/storage/hot"
|
path_src="/storage/hot"
|
||||||
path_mount="/storage/cold_1"
|
path_mount="/storage/cold_1"
|
||||||
path_backup="''${path_mount}/backup"
|
path_backup="''${path_mount}/backup"
|
||||||
path_container="''${path_backup}/home"
|
path_data="''${path_backup}/home"
|
||||||
path_media="/storage/cold_1 /storage/cold_2"
|
path_media="/storage/cold_1 /storage/cold_2"
|
||||||
|
|
||||||
# Check if backup drive is mounted.
|
# Check if backup drive is mounted.
|
||||||
|
@ -41,10 +41,10 @@
|
||||||
archive ColdMedia.txt && rm ColdMedia.txt || report "Backup : Failed to archive media list!"
|
archive ColdMedia.txt && rm ColdMedia.txt || report "Backup : Failed to archive media list!"
|
||||||
cd -
|
cd -
|
||||||
|
|
||||||
# Backup containers.
|
# Backup data.
|
||||||
container=$(archive container/)
|
data=$(archive data/)
|
||||||
bupsize=$(tdu ''${container} | awk '{print $1}')
|
bupsize=$(tdu ''${data} | awk '{print $1}')
|
||||||
mv ''${container} ''${path_container}/ || report "Backup : Failed to save containers!"
|
mv ''${data} ''${path_data}/ || report "Backup : Failed to save data!"
|
||||||
|
|
||||||
# Backup some media.
|
# Backup some media.
|
||||||
cd ''${path_src}
|
cd ''${path_src}
|
||||||
|
@ -61,14 +61,9 @@
|
||||||
archive_prune ColdMediaTxt 30
|
archive_prune ColdMediaTxt 30
|
||||||
cd -
|
cd -
|
||||||
|
|
||||||
# Prune old container copies.
|
# Prune old data copies.
|
||||||
cd ''${path_container}
|
cd ''${path_data}
|
||||||
archive_prune Container 7
|
archive_prune Data 7
|
||||||
cd -
|
|
||||||
|
|
||||||
# Prune game saves.
|
|
||||||
cd "''${path_backup}/save/"
|
|
||||||
archive_prune
|
|
||||||
cd -
|
cd -
|
||||||
|
|
||||||
# Sync writes.
|
# Sync writes.
|
||||||
|
@ -90,6 +85,7 @@ in {
|
||||||
curl
|
curl
|
||||||
gawk
|
gawk
|
||||||
gnutar
|
gnutar
|
||||||
|
mount
|
||||||
procps
|
procps
|
||||||
pv
|
pv
|
||||||
xz
|
xz
|
||||||
|
|
40
host/x86_64-linux/home/Bind.nix
Normal file
40
host/x86_64-linux/home/Bind.nix
Normal file
|
@ -0,0 +1,40 @@
|
||||||
|
{
|
||||||
|
lib,
|
||||||
|
...
|
||||||
|
}: let
|
||||||
|
storage = "/storage/hot/data";
|
||||||
|
|
||||||
|
binds = [
|
||||||
|
(mkBind "change" "/var/lib/changedetection-io")
|
||||||
|
(mkBind "cups" "/var/lib/cups")
|
||||||
|
(mkBind "deluge" "/var/lib/deluge/.config/deluge")
|
||||||
|
(mkBind "dkim" "/var/dkim")
|
||||||
|
(mkBind "dovecot_index" "/var/lib/dovecot/indices")
|
||||||
|
(mkBind "forgejo" "/var/lib/forgejo")
|
||||||
|
(mkBind "grocy" "/var/lib/grocy")
|
||||||
|
(mkBind "hass" "/var/lib/hass")
|
||||||
|
(mkBind "jellyfin" "/var/lib/jellyfin")
|
||||||
|
(mkBind "jellyfin_cache" "/var/cache/jellyfin")
|
||||||
|
(mkBind "kavita" "/var/lib/kavita")
|
||||||
|
(mkBind "letsencrypt" "/etc/letsencrypt")
|
||||||
|
(mkBind "nextcloud" "/var/lib/nextcloud")
|
||||||
|
(mkBind "ovpn" "/var/lib/ovpn")
|
||||||
|
(mkBind "paperless" "/var/lib/paperless")
|
||||||
|
(mkBind "postgres" "/var/lib/postgresql")
|
||||||
|
(mkBind "rabbitmq" "/var/lib/rabbitmq")
|
||||||
|
(mkBind "sieve" "/var/sieve")
|
||||||
|
(mkBind "terraria" "/var/lib/terraria")
|
||||||
|
(mkBind "uptime_kuma" "/var/lib/uptime-kuma")
|
||||||
|
(mkBind "vaultwarden" "/var/lib/vaultwarden")
|
||||||
|
(mkBind "vmail" "/var/vmail")
|
||||||
|
];
|
||||||
|
|
||||||
|
mkBind = name: path: {
|
||||||
|
${path} = {
|
||||||
|
device = "${storage}/${name}";
|
||||||
|
options = [ "bind" "nofail" "X-mount.mkdir=1777" ];
|
||||||
|
};
|
||||||
|
};
|
||||||
|
in {
|
||||||
|
fileSystems = lib.foldl' (acc: bind: acc // bind) { } binds;
|
||||||
|
}
|
97
host/x86_64-linux/home/Blocky.nix
Normal file
97
host/x86_64-linux/home/Blocky.nix
Normal file
|
@ -0,0 +1,97 @@
|
||||||
|
{ ... }: {
|
||||||
|
services.blocky = {
|
||||||
|
enable = true;
|
||||||
|
# REF: https://0xerr0r.github.io/blocky/main/configuration/
|
||||||
|
settings = {
|
||||||
|
bootstrapDns = "tcp+udp:1.1.1.1";
|
||||||
|
ports.dns = 53;
|
||||||
|
# connectIPVersion = "v4";
|
||||||
|
# httpPort = "80";
|
||||||
|
upstreams.groups = {
|
||||||
|
default = [
|
||||||
|
"https://dns.quad9.net/dns-query"
|
||||||
|
];
|
||||||
|
};
|
||||||
|
caching = {
|
||||||
|
maxItemsCount = 100000;
|
||||||
|
maxTime = "30m";
|
||||||
|
minTime = "5m";
|
||||||
|
prefetchExpires = "2h";
|
||||||
|
prefetchMaxItemsCount = 100000;
|
||||||
|
prefetchThreshold = 5;
|
||||||
|
prefetching = true;
|
||||||
|
};
|
||||||
|
blocking = {
|
||||||
|
blockTTL = "1m";
|
||||||
|
blockType = "zeroIP";
|
||||||
|
loading = {
|
||||||
|
refreshPeriod = "24h";
|
||||||
|
strategy = "blocking";
|
||||||
|
downloads = {
|
||||||
|
attempts = 3;
|
||||||
|
cooldown = "10s";
|
||||||
|
timeout = "5m";
|
||||||
|
};
|
||||||
|
};
|
||||||
|
# SRC: https://oisd.nl
|
||||||
|
# SRC: https://v.firebog.net
|
||||||
|
denylists = {
|
||||||
|
suspicious = [
|
||||||
|
"https://raw.githubusercontent.com/PolishFiltersTeam/KADhosts/master/KADhosts.txt"
|
||||||
|
"https://raw.githubusercontent.com/StevenBlack/hosts/master/hosts" # https://github.com/StevenBlack/hosts
|
||||||
|
"https://v.firebog.net/hosts/static/w3kbl.txt"
|
||||||
|
];
|
||||||
|
ads = [
|
||||||
|
"https://pgl.yoyo.org/adservers/serverlist.php?hostformat=hosts&showintro=0&mimetype=plaintext"
|
||||||
|
"https://raw.githubusercontent.com/bigdargon/hostsVN/master/hosts"
|
||||||
|
"https://v.firebog.net/hosts/AdguardDNS.txt"
|
||||||
|
"https://v.firebog.net/hosts/Admiral.txt"
|
||||||
|
"https://v.firebog.net/hosts/Easylist.txt"
|
||||||
|
];
|
||||||
|
tracking = [
|
||||||
|
"https://hostfiles.frogeye.fr/firstparty-trackers-hosts.txt"
|
||||||
|
"https://v.firebog.net/hosts/Easyprivacy.txt"
|
||||||
|
"https://v.firebog.net/hosts/Prigent-Ads.txt"
|
||||||
|
];
|
||||||
|
malicious = [
|
||||||
|
"https://gitlab.com/quidsup/notrack-blocklists/raw/master/notrack-malware.txt"
|
||||||
|
"https://osint.digitalside.it/Threat-Intel/lists/latestdomains.txt"
|
||||||
|
"https://phishing.army/download/phishing_army_blocklist_extended.txt"
|
||||||
|
"https://raw.githubusercontent.com/AssoEchap/stalkerware-indicators/master/generated/hosts"
|
||||||
|
"https://raw.githubusercontent.com/Spam404/lists/master/main-blacklist.txt"
|
||||||
|
"https://urlhaus.abuse.ch/downloads/hostfile/"
|
||||||
|
"https://v.firebog.net/hosts/Prigent-Crypto.txt"
|
||||||
|
"https://v.firebog.net/hosts/Prigent-Malware.txt"
|
||||||
|
];
|
||||||
|
other = [
|
||||||
|
"https://big.oisd.nl/domainswild"
|
||||||
|
"https://zerodot1.gitlab.io/CoinBlockerLists/hosts_browser"
|
||||||
|
];
|
||||||
|
};
|
||||||
|
# allowlists = {
|
||||||
|
# other = [
|
||||||
|
# "/.*.vk.com/"
|
||||||
|
# ];
|
||||||
|
# };
|
||||||
|
clientGroupsBlock = {
|
||||||
|
default = [
|
||||||
|
"ads"
|
||||||
|
"malicious"
|
||||||
|
"other"
|
||||||
|
"suspicious"
|
||||||
|
"tracking"
|
||||||
|
];
|
||||||
|
};
|
||||||
|
};
|
||||||
|
customDNS.mapping = let
|
||||||
|
block = host: { ${host} = "0.0.0.0"; };
|
||||||
|
in {
|
||||||
|
"voronind.com" = "10.0.0.1,fd09:8d46:b26::1";
|
||||||
|
}
|
||||||
|
// block "gosuslugi.ru"
|
||||||
|
// block "rutube.ru"
|
||||||
|
# // block "vk.com"
|
||||||
|
;
|
||||||
|
};
|
||||||
|
};
|
||||||
|
}
|
9
host/x86_64-linux/home/Change.nix
Normal file
9
host/x86_64-linux/home/Change.nix
Normal file
|
@ -0,0 +1,9 @@
|
||||||
|
{ ... }: {
|
||||||
|
services.changedetection-io = {
|
||||||
|
enable = true;
|
||||||
|
baseURL = "change.voronind.com";
|
||||||
|
behindProxy = true;
|
||||||
|
listenAddress = "0.0.0.0";
|
||||||
|
port = 5001;
|
||||||
|
};
|
||||||
|
}
|
|
@ -1,88 +0,0 @@
|
||||||
{ ... }: {
|
|
||||||
container = {
|
|
||||||
enable = true;
|
|
||||||
autoStart = true;
|
|
||||||
domain = "voronind.com";
|
|
||||||
host = "188.242.247.132";
|
|
||||||
interface = "enp8s0";
|
|
||||||
localAccess = "10.0.0.0/24";
|
|
||||||
storage = "/storage/hot/container";
|
|
||||||
module = {
|
|
||||||
change.enable = true;
|
|
||||||
cloud.enable = true;
|
|
||||||
dns.enable = true;
|
|
||||||
download.enable = true;
|
|
||||||
frkn.enable = true;
|
|
||||||
git.enable = true;
|
|
||||||
home.enable = true;
|
|
||||||
iot.enable = true;
|
|
||||||
jobber.enable = true;
|
|
||||||
mail.enable = true;
|
|
||||||
office.enable = true;
|
|
||||||
paper.enable = true;
|
|
||||||
pass.enable = true;
|
|
||||||
paste.enable = true;
|
|
||||||
postgres.enable = true;
|
|
||||||
print.enable = true;
|
|
||||||
proxy.enable = true;
|
|
||||||
rabbitmq.enable = true;
|
|
||||||
read.enable = true;
|
|
||||||
redis.enable = true;
|
|
||||||
search.enable = true;
|
|
||||||
status.enable = true;
|
|
||||||
stock.enable = true;
|
|
||||||
terraria.enable = true;
|
|
||||||
vpn.enable = true;
|
|
||||||
watch.enable = true;
|
|
||||||
yt.enable = true;
|
|
||||||
};
|
|
||||||
media = {
|
|
||||||
anime = [
|
|
||||||
"/storage/cold_1/anime"
|
|
||||||
"/storage/cold_2/anime"
|
|
||||||
];
|
|
||||||
book = [
|
|
||||||
"/storage/hot/book"
|
|
||||||
];
|
|
||||||
download = [
|
|
||||||
"/storage/hot/download"
|
|
||||||
];
|
|
||||||
manga = [
|
|
||||||
"/storage/cold_1/manga"
|
|
||||||
"/storage/cold_2/manga"
|
|
||||||
];
|
|
||||||
movie = [
|
|
||||||
"/storage/cold_1/movie"
|
|
||||||
"/storage/cold_2/movie"
|
|
||||||
];
|
|
||||||
music = [
|
|
||||||
"/storage/cold_2/music"
|
|
||||||
];
|
|
||||||
paper = [
|
|
||||||
"/storage/hot/paper"
|
|
||||||
];
|
|
||||||
porn = [
|
|
||||||
"/storage/cold_2/porn"
|
|
||||||
];
|
|
||||||
photo = [
|
|
||||||
"/storage/hot/container/cloud/data/data/cakee/files/photo"
|
|
||||||
"/storage/cold_1/backup/tmp/photo"
|
|
||||||
];
|
|
||||||
show = [
|
|
||||||
"/storage/cold_1/show"
|
|
||||||
"/storage/cold_2/show"
|
|
||||||
];
|
|
||||||
study = [
|
|
||||||
"/storage/cold_1/study"
|
|
||||||
"/storage/cold_2/study"
|
|
||||||
];
|
|
||||||
work = [
|
|
||||||
"/storage/cold_2/work"
|
|
||||||
];
|
|
||||||
youtube = [
|
|
||||||
"/storage/cold_1/youtube"
|
|
||||||
"/storage/cold_2/youtube"
|
|
||||||
];
|
|
||||||
};
|
|
||||||
};
|
|
||||||
}
|
|
22
host/x86_64-linux/home/Cups.nix
Normal file
22
host/x86_64-linux/home/Cups.nix
Normal file
|
@ -0,0 +1,22 @@
|
||||||
|
# NOTE: Login to contaier, run passwd and use that root/pw combo for administration. `AllowFrom = all` doesn't seem to work.
|
||||||
|
# ipp://10.0.0.10
|
||||||
|
# Pantum M6500W-Series
|
||||||
|
{
|
||||||
|
__findFile,
|
||||||
|
pkgs,
|
||||||
|
...
|
||||||
|
} @args: let
|
||||||
|
package = pkgs.callPackage <package/print> args;
|
||||||
|
in {
|
||||||
|
services.printing = {
|
||||||
|
enable = true;
|
||||||
|
allowFrom = [ "all" ];
|
||||||
|
browsing = true;
|
||||||
|
defaultShared = true;
|
||||||
|
drivers = [ package ];
|
||||||
|
listenAddresses = [ "0.0.0.0:631" ];
|
||||||
|
startWhenNeeded = true;
|
||||||
|
stateless = false;
|
||||||
|
webInterface = true;
|
||||||
|
};
|
||||||
|
}
|
23
host/x86_64-linux/home/Ddns.nix
Normal file
23
host/x86_64-linux/home/Ddns.nix
Normal file
|
@ -0,0 +1,23 @@
|
||||||
|
{ ... }: {
|
||||||
|
services.cloudflare-dyndns = {
|
||||||
|
enable = true;
|
||||||
|
apiTokenFile = "/storage/hot/data/CfToken";
|
||||||
|
deleteMissing = false;
|
||||||
|
ipv4 = true;
|
||||||
|
ipv6 = true;
|
||||||
|
proxied = false;
|
||||||
|
domains = let
|
||||||
|
domain = "voronind.com";
|
||||||
|
in [
|
||||||
|
domain
|
||||||
|
] ++ map (sub: "${sub}.${domain}") [
|
||||||
|
"cloud"
|
||||||
|
"git"
|
||||||
|
"mail"
|
||||||
|
"office"
|
||||||
|
"paste"
|
||||||
|
"play"
|
||||||
|
"vpn"
|
||||||
|
];
|
||||||
|
};
|
||||||
|
}
|
14
host/x86_64-linux/home/Deluge.nix
Normal file
14
host/x86_64-linux/home/Deluge.nix
Normal file
|
@ -0,0 +1,14 @@
|
||||||
|
{
|
||||||
|
lib,
|
||||||
|
...
|
||||||
|
}: {
|
||||||
|
services.deluge = {
|
||||||
|
enable = true;
|
||||||
|
web.enable = true;
|
||||||
|
};
|
||||||
|
systemd.services.deluged.serviceConfig = {
|
||||||
|
MemoryMax = "4G";
|
||||||
|
Restart = lib.mkForce "always";
|
||||||
|
RuntimeMaxSec = "3h";
|
||||||
|
};
|
||||||
|
}
|
54
host/x86_64-linux/home/Forgejo.nix
Normal file
54
host/x86_64-linux/home/Forgejo.nix
Normal file
|
@ -0,0 +1,54 @@
|
||||||
|
{ ... }: {
|
||||||
|
services.forgejo = {
|
||||||
|
enable = true;
|
||||||
|
stateDir = "/var/lib/forgejo";
|
||||||
|
|
||||||
|
database = {
|
||||||
|
createDatabase = true;
|
||||||
|
name = "forgejo";
|
||||||
|
type = "postgres";
|
||||||
|
user = "forgejo";
|
||||||
|
};
|
||||||
|
|
||||||
|
settings = let
|
||||||
|
gcArgs = "--aggressive --no-cruft --prune=now";
|
||||||
|
gcTimeout = 600;
|
||||||
|
in {
|
||||||
|
"cron.cleanup_actions".ENABLED = true;
|
||||||
|
"cron.update_mirrors".SCHEDULE = "@midnight";
|
||||||
|
"git".GC_ARGS = gcArgs;
|
||||||
|
"git.timeout".GC = gcTimeout;
|
||||||
|
"log".LEVEL = "Error";
|
||||||
|
"repo-archive".ENABLED = false;
|
||||||
|
"repository.issue".MAX_PINNED = 99999;
|
||||||
|
"repository.pull-request".DEFAULT_MERGE_STYLE = "rebase";
|
||||||
|
"service".DISABLE_REGISTRATION = true;
|
||||||
|
"server" = {
|
||||||
|
DOMAIN = "git.voronind.com";
|
||||||
|
HTTP_ADDR = "0.0.0.0";
|
||||||
|
ROOT_URL = "https://git.voronind.com";
|
||||||
|
BUILTIN_SSH_SERVER_USER = "git";
|
||||||
|
DISABLE_SSH = false;
|
||||||
|
SSH_PORT = 22144;
|
||||||
|
START_SSH_SERVER = true;
|
||||||
|
};
|
||||||
|
"ui" = {
|
||||||
|
AMBIGUOUS_UNICODE_DETECTION = false;
|
||||||
|
};
|
||||||
|
"repository" = {
|
||||||
|
DEFAULT_PRIVATE = "private";
|
||||||
|
DEFAULT_PUSH_CREATE_PRIVATE = true;
|
||||||
|
};
|
||||||
|
"cron" = {
|
||||||
|
ENABLED = true;
|
||||||
|
RUN_AT_START = true;
|
||||||
|
};
|
||||||
|
"cron.git_gc_repos" = {
|
||||||
|
ENABLED = true;
|
||||||
|
ARGS = gcArgs;
|
||||||
|
SCHEDULE = "@midnight";
|
||||||
|
TIMEOUT = gcTimeout;
|
||||||
|
};
|
||||||
|
};
|
||||||
|
};
|
||||||
|
}
|
41
host/x86_64-linux/home/Frkn.nix
Normal file
41
host/x86_64-linux/home/Frkn.nix
Normal file
|
@ -0,0 +1,41 @@
|
||||||
|
{
|
||||||
|
pkgs,
|
||||||
|
...
|
||||||
|
}: {
|
||||||
|
services = {
|
||||||
|
tor = {
|
||||||
|
enable = true;
|
||||||
|
openFirewall = true;
|
||||||
|
settings = let
|
||||||
|
exclude = "{RU},{UA},{BY},{KZ},{CN},{??}";
|
||||||
|
in {
|
||||||
|
# ExcludeExitNodes = exclude;
|
||||||
|
# ExcludeNodes = exclude;
|
||||||
|
# DNSPort = dnsport;
|
||||||
|
UseBridges = true;
|
||||||
|
ClientTransportPlugin = "obfs4 exec ${pkgs.obfs4}/bin/lyrebird";
|
||||||
|
Bridge = [
|
||||||
|
"obfs4 121.45.140.249:12123 0922E212E33B04F0B7C1E398161E8EDE06734F26 cert=3AQ4iJFAzxzt7a/zgXIiFEs6fvrXInXt1Dtr09DgnpvUzG/iiyRTdXYZKSYpI124Zt3ZUA iat-mode=0"
|
||||||
|
"obfs4 145.239.31.71:10161 882125D15B59BB82BE66F999056CB676D3F061F8 cert=AnD+EvcBMuQDVM7PwW7NgFAzW1M5jDm7DjQtIIcBSjoyAf1FJ2p535rrYL2Kk8POAd0+aw iat-mode=0"
|
||||||
|
"obfs4 79.137.11.45:45072 ECA3197D49A29DDECD4ACBF9BCF15E4987B78137 cert=2FKyLWkPgMNCWxBD3cNOTRxJH3XP+HdStPGKMjJfw2YbvVjihIp3X2BCrtxQya9m5II5XA iat-mode=0"
|
||||||
|
"obfs4 94.103.89.153:4443 5617848964FD6546968B5BF3FFA6C11BCCABE58B cert=tYsmuuTe9phJS0Gh8NKIpkVZP/XKs7gJCqi31o8LClwYetxzFz0fQZgsMwhNcIlZ0HG5LA iat-mode=0"
|
||||||
|
];
|
||||||
|
};
|
||||||
|
client = {
|
||||||
|
enable = true;
|
||||||
|
# dns.enable = true;
|
||||||
|
socksListenAddress = {
|
||||||
|
IsolateDestAddr = true;
|
||||||
|
port = 9050;
|
||||||
|
# addr = cfg.address;
|
||||||
|
# port = cfg.torport;
|
||||||
|
};
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
xray = {
|
||||||
|
enable = true;
|
||||||
|
settingsFile = "/storage/hot/data/XrayClient.json";
|
||||||
|
};
|
||||||
|
};
|
||||||
|
}
|
16
host/x86_64-linux/home/Grocy.nix
Normal file
16
host/x86_64-linux/home/Grocy.nix
Normal file
|
@ -0,0 +1,16 @@
|
||||||
|
{ ... }: {
|
||||||
|
services.grocy = {
|
||||||
|
enable = true;
|
||||||
|
# dataDir = "/var/lib/grocy";
|
||||||
|
hostName = "stock.voronind.com";
|
||||||
|
nginx.enableSSL = false;
|
||||||
|
settings = {
|
||||||
|
calendar = {
|
||||||
|
firstDayOfWeek = 1;
|
||||||
|
showWeekNumber = true;
|
||||||
|
};
|
||||||
|
culture = "en";
|
||||||
|
currency = "RUB";
|
||||||
|
};
|
||||||
|
};
|
||||||
|
}
|
45
host/x86_64-linux/home/Hass.nix
Normal file
45
host/x86_64-linux/home/Hass.nix
Normal file
|
@ -0,0 +1,45 @@
|
||||||
|
{ ... }: {
|
||||||
|
# Allow Hass to talk to Zigbee dongle.
|
||||||
|
users.users.hass.extraGroups = [
|
||||||
|
"dialout"
|
||||||
|
"tty"
|
||||||
|
];
|
||||||
|
|
||||||
|
services.home-assistant = {
|
||||||
|
# NOTE: Missing: hacs. Inside hacs: `card-mod`, `Clock Weather Card`, `WallPanel` and `Yandex.Station`.
|
||||||
|
enable = true;
|
||||||
|
# NOTE: Using imperative config because of secrets.
|
||||||
|
config = null;
|
||||||
|
extraComponents = [
|
||||||
|
"caldav"
|
||||||
|
"met"
|
||||||
|
"sun"
|
||||||
|
"systemmonitor"
|
||||||
|
"zha"
|
||||||
|
];
|
||||||
|
extraPackages = python3Packages: with python3Packages; [
|
||||||
|
aiodhcpwatcher
|
||||||
|
aiodiscover
|
||||||
|
aiogithubapi
|
||||||
|
arrow
|
||||||
|
async-upnp-client
|
||||||
|
av
|
||||||
|
go2rtc-client
|
||||||
|
gtts
|
||||||
|
ha-ffmpeg
|
||||||
|
hassil
|
||||||
|
home-assistant-intents
|
||||||
|
mutagen
|
||||||
|
numpy
|
||||||
|
pymicro-vad
|
||||||
|
pynacl
|
||||||
|
pyspeex-noise
|
||||||
|
python-telegram-bot
|
||||||
|
pyturbojpeg
|
||||||
|
zeroconf
|
||||||
|
];
|
||||||
|
# lovelaceConfig = {
|
||||||
|
# title = "Home IoT control center.";
|
||||||
|
# };
|
||||||
|
};
|
||||||
|
}
|
15
host/x86_64-linux/home/Homer.nix
Normal file
15
host/x86_64-linux/home/Homer.nix
Normal file
|
@ -0,0 +1,15 @@
|
||||||
|
{
|
||||||
|
__findFile,
|
||||||
|
pkgs,
|
||||||
|
util,
|
||||||
|
...
|
||||||
|
} @args: let
|
||||||
|
package = (pkgs.callPackage <package/homer> args);
|
||||||
|
in {
|
||||||
|
services.nginx = {
|
||||||
|
enable = true;
|
||||||
|
virtualHosts."home.voronind.com" = {
|
||||||
|
root = "${package}";
|
||||||
|
};
|
||||||
|
};
|
||||||
|
}
|
31
host/x86_64-linux/home/Invidious.nix
Normal file
31
host/x86_64-linux/home/Invidious.nix
Normal file
|
@ -0,0 +1,31 @@
|
||||||
|
{
|
||||||
|
__findFile,
|
||||||
|
config,
|
||||||
|
inputs,
|
||||||
|
pkgs,
|
||||||
|
pkgsMaster,
|
||||||
|
...
|
||||||
|
}: {
|
||||||
|
disabledModules = [ "services/web-apps/invidious.nix" ];
|
||||||
|
imports = [ "${inputs.nixpkgsMaster}/nixos/modules/services/web-apps/invidious.nix" ];
|
||||||
|
|
||||||
|
services.invidious = {
|
||||||
|
enable = true;
|
||||||
|
domain = "yt.voronind.com";
|
||||||
|
package = pkgsMaster.invidious;
|
||||||
|
port = 3001;
|
||||||
|
nginx.enable = false;
|
||||||
|
database = {
|
||||||
|
createLocally = true;
|
||||||
|
# passwordFile = "${pkgs.writeText "InvidiousDbPassword" "invidious"}";
|
||||||
|
};
|
||||||
|
settings = {
|
||||||
|
admins = [ "root" ];
|
||||||
|
captcha_enabled = false;
|
||||||
|
check_tables = true;
|
||||||
|
external_port = 443;
|
||||||
|
https_only = true;
|
||||||
|
registration_enabled = false;
|
||||||
|
};
|
||||||
|
};
|
||||||
|
}
|
14
host/x86_64-linux/home/Jellyfin.nix
Normal file
14
host/x86_64-linux/home/Jellyfin.nix
Normal file
|
@ -0,0 +1,14 @@
|
||||||
|
{ ... }: {
|
||||||
|
# systemd.services.jellyfin.serviceConfig.MemoryMax = cfg.memLimit;
|
||||||
|
|
||||||
|
users.users.jellyfin.extraGroups = [
|
||||||
|
"video"
|
||||||
|
"render"
|
||||||
|
];
|
||||||
|
|
||||||
|
services.jellyfin = {
|
||||||
|
enable = true;
|
||||||
|
# cacheDir = "/var/cache/jellyfin";
|
||||||
|
# dataDir = "/var/lib/jellyfin";
|
||||||
|
};
|
||||||
|
}
|
70
host/x86_64-linux/home/Jobber.nix
Normal file
70
host/x86_64-linux/home/Jobber.nix
Normal file
|
@ -0,0 +1,70 @@
|
||||||
|
# Use `nixos-container login jobber` as root and empty pw.
|
||||||
|
{
|
||||||
|
__findFile,
|
||||||
|
const,
|
||||||
|
lib,
|
||||||
|
pkgsJobber,
|
||||||
|
poetry2nixJobber,
|
||||||
|
...
|
||||||
|
}: let
|
||||||
|
script = import <package/jobber> {
|
||||||
|
pkgs = pkgsJobber;
|
||||||
|
poetry2nix = poetry2nixJobber;
|
||||||
|
};
|
||||||
|
in {
|
||||||
|
networking.nat = {
|
||||||
|
enable = true;
|
||||||
|
externalInterface = "enp8s0";
|
||||||
|
internalInterfaces = [ "ve-+" ];
|
||||||
|
};
|
||||||
|
|
||||||
|
containers.jobber = {
|
||||||
|
autoStart = true;
|
||||||
|
enableTun = true;
|
||||||
|
privateNetwork = true;
|
||||||
|
hostAddress = "188.242.247.132";
|
||||||
|
localAddress = "10.1.0.2";
|
||||||
|
|
||||||
|
config = { ... }: let
|
||||||
|
packages = [
|
||||||
|
script
|
||||||
|
] ++ (with pkgsJobber; [
|
||||||
|
firefox
|
||||||
|
geckodriver
|
||||||
|
openvpn
|
||||||
|
python311
|
||||||
|
]);
|
||||||
|
in {
|
||||||
|
boot.isContainer = true;
|
||||||
|
system.stateVersion = const.stateVersion;
|
||||||
|
users = {
|
||||||
|
users.root.password = "";
|
||||||
|
mutableUsers = false;
|
||||||
|
};
|
||||||
|
networking = {
|
||||||
|
useHostResolvConf = lib.mkForce false;
|
||||||
|
nameservers = [
|
||||||
|
"10.30.218.2"
|
||||||
|
];
|
||||||
|
};
|
||||||
|
|
||||||
|
systemd.services.jobber = {
|
||||||
|
description = "My job is pushing the button.";
|
||||||
|
enable = true;
|
||||||
|
path = packages;
|
||||||
|
wantedBy = [
|
||||||
|
"multi-user.target"
|
||||||
|
];
|
||||||
|
environment = {
|
||||||
|
PYTHONDONTWRITEBYTECODE = "1";
|
||||||
|
PYTHONUNBUFFERED = "1";
|
||||||
|
};
|
||||||
|
serviceConfig = {
|
||||||
|
ExecStart = "${script}/bin/jobber -u";
|
||||||
|
Restart = "on-failure";
|
||||||
|
Type = "simple";
|
||||||
|
};
|
||||||
|
};
|
||||||
|
};
|
||||||
|
};
|
||||||
|
}
|
13
host/x86_64-linux/home/Kavita.nix
Normal file
13
host/x86_64-linux/home/Kavita.nix
Normal file
|
@ -0,0 +1,13 @@
|
||||||
|
{
|
||||||
|
pkgs,
|
||||||
|
...
|
||||||
|
}: {
|
||||||
|
services.kavita = {
|
||||||
|
enable = true;
|
||||||
|
tokenKeyFile = pkgs.writeText "KavitaToken" "xY19aQOa939/Ie6GCRGbubVK8zRwrgBY/20AuyMpYshUjwK1Uyl7bw1yknVh6jJIFIfwq2vAjeotOUq7NEsf9Q==";
|
||||||
|
settings = {
|
||||||
|
# IpAddresses = cfg.address;
|
||||||
|
Port = 5000;
|
||||||
|
};
|
||||||
|
};
|
||||||
|
}
|
166
host/x86_64-linux/home/Mailserver.nix
Normal file
166
host/x86_64-linux/home/Mailserver.nix
Normal file
|
@ -0,0 +1,166 @@
|
||||||
|
# REF: https://nixos-mailserver.readthedocs.io/en/latest/setup-guide.html
|
||||||
|
{
|
||||||
|
pkgs,
|
||||||
|
util,
|
||||||
|
...
|
||||||
|
}: let
|
||||||
|
domain = "voronind.com";
|
||||||
|
|
||||||
|
# SEE: https://gitlab.com/simple-nixos-mailserver/nixos-mailserver#release-branches
|
||||||
|
version = "24.05";
|
||||||
|
sha256 = "sha256:0clvw4622mqzk1aqw1qn6shl9pai097q62mq1ibzscnjayhp278b";
|
||||||
|
in {
|
||||||
|
imports = [
|
||||||
|
(builtins.fetchTarball {
|
||||||
|
inherit sha256;
|
||||||
|
url = "https://gitlab.com/simple-nixos-mailserver/nixos-mailserver/-/archive/nixos-${version}/nixos-mailserver-nixos-${version}.tar.gz";
|
||||||
|
})
|
||||||
|
];
|
||||||
|
|
||||||
|
mailserver = {
|
||||||
|
enable = true;
|
||||||
|
domains = [ domain ];
|
||||||
|
fqdn = "mail.${domain}";
|
||||||
|
sendingFqdn = domain;
|
||||||
|
localDnsResolver = false;
|
||||||
|
|
||||||
|
# Use `mkpasswd -sm bcrypt`.
|
||||||
|
loginAccounts = let
|
||||||
|
defaultQuota = "1G";
|
||||||
|
in {
|
||||||
|
"admin@${domain}" = {
|
||||||
|
hashedPassword = "$2b$05$1O.dxXxaVshcBNybcqDRYuTlnYt3jDBwfPZWoDtP4BjOLoL0StYsi";
|
||||||
|
name = "admin";
|
||||||
|
quota = defaultQuota;
|
||||||
|
};
|
||||||
|
"account@${domain}" = {
|
||||||
|
hashedPassword = "$2b$05$sCyZHdk98KqQ1qsTIvbrUeRJlNBOwBqDgpdc1QxiSnONlEkZ8xGNO";
|
||||||
|
name = "account";
|
||||||
|
quota = defaultQuota;
|
||||||
|
};
|
||||||
|
"hi@${domain}" = {
|
||||||
|
hashedPassword = "$2b$05$6fT5hIhzIasNfp9IQr/ds.5RuxH95VKU3QJWlX3hmrAzDF3mExanq";
|
||||||
|
name = "hi";
|
||||||
|
quota = defaultQuota;
|
||||||
|
aliases = [
|
||||||
|
"voronind@${domain}"
|
||||||
|
];
|
||||||
|
};
|
||||||
|
"job@${domain}" = {
|
||||||
|
hashedPassword = "$2b$05$.sUmv2.9EWPfLwJn/oZw2e1UbR7HrpNQ2THc5jjX3ysy7CY8ZWHUC";
|
||||||
|
name = "job";
|
||||||
|
quota = defaultQuota;
|
||||||
|
};
|
||||||
|
"trash@${domain}" = {
|
||||||
|
hashedPassword = "$2b$05$kn5ygZjN9NR3LXjnKKRw/.DXaZQNW.1XEottlCFIoKiDpIj.JGLJm";
|
||||||
|
name = "trash";
|
||||||
|
quota = defaultQuota;
|
||||||
|
catchAll = [
|
||||||
|
domain
|
||||||
|
];
|
||||||
|
};
|
||||||
|
"noreply@${domain}" = {
|
||||||
|
hashedPassword = "$2b$05$TaKwoYmcmkAhsRRv6xG5wOkChcz50cB9BP6QPUDKNAcxMbrY6AeMK";
|
||||||
|
name = "noreply";
|
||||||
|
quota = defaultQuota;
|
||||||
|
sendOnly = true;
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
enableImap = true;
|
||||||
|
enableImapSsl = true;
|
||||||
|
enableSubmission = true;
|
||||||
|
enableSubmissionSsl = true;
|
||||||
|
|
||||||
|
enableManageSieve = true;
|
||||||
|
virusScanning = false;
|
||||||
|
|
||||||
|
certificateFile = "/etc/letsencrypt/live/${domain}/cert.pem";
|
||||||
|
certificateScheme = "manual";
|
||||||
|
keyFile = "/etc/letsencrypt/live/${domain}/privkey.pem";
|
||||||
|
|
||||||
|
dkimKeyDirectory = "/var/dkim";
|
||||||
|
indexDir = "/var/lib/dovecot/indices";
|
||||||
|
mailDirectory = "/var/vmail";
|
||||||
|
sieveDirectory = "/var/sieve";
|
||||||
|
|
||||||
|
mailboxes = let
|
||||||
|
mkSpecialBox = specialUse: {
|
||||||
|
${specialUse} = {
|
||||||
|
inherit specialUse;
|
||||||
|
auto = "subscribe";
|
||||||
|
};
|
||||||
|
};
|
||||||
|
in builtins.foldl' (acc: box: acc // (mkSpecialBox box)) {} [
|
||||||
|
"All"
|
||||||
|
"Archive"
|
||||||
|
"Drafts"
|
||||||
|
"Junk"
|
||||||
|
"Sent"
|
||||||
|
"Trash"
|
||||||
|
];
|
||||||
|
|
||||||
|
dmarcReporting = {
|
||||||
|
inherit domain;
|
||||||
|
enable = true;
|
||||||
|
organizationName = "voronind";
|
||||||
|
# email = "noreply@${domain}";
|
||||||
|
};
|
||||||
|
|
||||||
|
# monitoring = {
|
||||||
|
# enable = true;
|
||||||
|
# alertAddress = "admin@${domain}";
|
||||||
|
# };
|
||||||
|
};
|
||||||
|
|
||||||
|
services = {
|
||||||
|
roundcube = {
|
||||||
|
enable = true;
|
||||||
|
hostName = "mail.${domain}";
|
||||||
|
dicts = with pkgs.aspellDicts; [
|
||||||
|
en
|
||||||
|
ru
|
||||||
|
];
|
||||||
|
plugins = [
|
||||||
|
"managesieve"
|
||||||
|
];
|
||||||
|
extraConfig = util.trimTabs ''
|
||||||
|
$config['smtp_server'] = "localhost:25";
|
||||||
|
$config['smtp_auth_type'] = null;
|
||||||
|
$config['smtp_user'] = "";
|
||||||
|
$config['smtp_pass'] = "";
|
||||||
|
# $config['smtp_user'] = "%u";
|
||||||
|
# $config['smtp_pass'] = "%p";
|
||||||
|
'';
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
systemd = {
|
||||||
|
services.autoexpunge = {
|
||||||
|
description = "Delete old mail";
|
||||||
|
serviceConfig = {
|
||||||
|
Type = "oneshot";
|
||||||
|
};
|
||||||
|
path = [
|
||||||
|
pkgs.dovecot
|
||||||
|
];
|
||||||
|
script = util.trimTabs ''
|
||||||
|
doveadm expunge -A mailbox Junk SENTBEFORE 7d
|
||||||
|
doveadm expunge -A mailbox Trash SENTBEFORE 30d
|
||||||
|
doveadm expunge -u trash@voronind.com mailbox Inbox SENTBEFORE 30d
|
||||||
|
doveadm purge -A
|
||||||
|
'';
|
||||||
|
};
|
||||||
|
|
||||||
|
timers.autoexpunge = {
|
||||||
|
timerConfig = {
|
||||||
|
OnCalendar = "daily";
|
||||||
|
Persistent = true;
|
||||||
|
Unit = "autoexpunge.service";
|
||||||
|
};
|
||||||
|
wantedBy = [
|
||||||
|
"timers.target"
|
||||||
|
];
|
||||||
|
};
|
||||||
|
};
|
||||||
|
}
|
|
@ -1,6 +1,5 @@
|
||||||
# 10.0.0.0/24 & fd09:8d46:0b26::/48 - phys clients (lan).
|
# 10.0.0.0/24 & fd09:8d46:0b26::/48 - phys clients (lan).
|
||||||
# 10.1.0.0/24 & fd76:c80a:8e86::/48 - containers.
|
# 10.0.1.0/24 - vpn clients.
|
||||||
# 10.1.1.0/24 - vpn clients.
|
|
||||||
{
|
{
|
||||||
config,
|
config,
|
||||||
const,
|
const,
|
||||||
|
@ -8,10 +7,8 @@
|
||||||
util,
|
util,
|
||||||
...
|
...
|
||||||
}: let
|
}: let
|
||||||
external = "188.242.247.132"; # Wan host IP address.
|
|
||||||
internal = "10.0.0.1"; # Lan host IP address.
|
internal = "10.0.0.1"; # Lan host IP address.
|
||||||
external6 = "2a05:3580:f42c:c800:aaa1:59ff:fe47:fda2"; # Wan host IP6 address.
|
internal6 = "fd09:8d46:b26:0:8079:82ff:fe1a:916a"; # Lan host IP6 address.
|
||||||
internal6 = "fd09:8d46:b26::1"; # Lan host IP6 address.
|
|
||||||
|
|
||||||
lan = "br0"; # Lan interface.
|
lan = "br0"; # Lan interface.
|
||||||
wan = "enp8s0"; # Wan interface.
|
wan = "enp8s0"; # Wan interface.
|
||||||
|
@ -19,6 +16,9 @@ in {
|
||||||
# Disable SSH access from everywhere, configure access bellow.
|
# Disable SSH access from everywhere, configure access bellow.
|
||||||
services.openssh.openFirewall = false;
|
services.openssh.openFirewall = false;
|
||||||
|
|
||||||
|
# Disable systemd-resolved for DNS server.
|
||||||
|
services.resolved.enable = false;
|
||||||
|
|
||||||
# NOTE: Debugging.
|
# NOTE: Debugging.
|
||||||
# systemd.services."systemd-networkd".environment.SYSTEMD_LOG_LEVEL = "debug";
|
# systemd.services."systemd-networkd".environment.SYSTEMD_LOG_LEVEL = "debug";
|
||||||
|
|
||||||
|
@ -82,7 +82,7 @@ in {
|
||||||
linkConfig.RequiredForOnline = "carrier";
|
linkConfig.RequiredForOnline = "carrier";
|
||||||
address = [
|
address = [
|
||||||
"${internal}/24"
|
"${internal}/24"
|
||||||
"${internal6}/48"
|
# "${internal6}/48"
|
||||||
];
|
];
|
||||||
networkConfig = {
|
networkConfig = {
|
||||||
DHCPPrefixDelegation = true;
|
DHCPPrefixDelegation = true;
|
||||||
|
@ -96,7 +96,7 @@ in {
|
||||||
};
|
};
|
||||||
ipv6Prefixes = [
|
ipv6Prefixes = [
|
||||||
{
|
{
|
||||||
AddressAutoconfiguration = true;
|
Assign = true;
|
||||||
Prefix = "${internal6}/64";
|
Prefix = "${internal6}/64";
|
||||||
}
|
}
|
||||||
];
|
];
|
||||||
|
@ -120,7 +120,7 @@ in {
|
||||||
UplinkInterface = wan;
|
UplinkInterface = wan;
|
||||||
};
|
};
|
||||||
dhcpServerStaticLeases = let
|
dhcpServerStaticLeases = let
|
||||||
mkStatic = Address: MACAddress: { dhcpServerStaticLeaseConfig = { inherit Address MACAddress; }; };
|
mkStatic = Address: MACAddress: { inherit Address MACAddress; };
|
||||||
in [
|
in [
|
||||||
# TODO: Add pocket.
|
# TODO: Add pocket.
|
||||||
(mkStatic "10.0.0.2" "9c:9d:7e:8e:3d:c7") # Wifi AP.
|
(mkStatic "10.0.0.2" "9c:9d:7e:8e:3d:c7") # Wifi AP.
|
||||||
|
@ -163,23 +163,9 @@ in {
|
||||||
logRefusedPackets = false;
|
logRefusedPackets = false;
|
||||||
logRefusedUnicastsOnly = true;
|
logRefusedUnicastsOnly = true;
|
||||||
|
|
||||||
extraCommands = let
|
extraCommands = util.trimTabs ''
|
||||||
# Container configs.
|
# Wan access for 10.0.0.0/8 subnet.
|
||||||
cfg = config.container.module;
|
iptables -t nat -A POSTROUTING -s 10.0.0.0/8 -d 0/0 -o ${wan} -j MASQUERADE
|
||||||
|
|
||||||
# Const.
|
|
||||||
tcp = "tcp";
|
|
||||||
udp = "udp";
|
|
||||||
|
|
||||||
# Create port forwarding rule.
|
|
||||||
mkForward = src: sport: dst: dport: proto: "iptables -t nat -I PREROUTING -d ${src} -p ${proto} --dport ${toString sport} -j DNAT --to-destination ${dst}:${toString dport}\n";
|
|
||||||
in (util.trimTabs ''
|
|
||||||
# Wan access for 10.0.0.0/24 subnet.
|
|
||||||
iptables -t nat -A POSTROUTING -s 10.0.0.0/24 -d 0/0 -o ${wan} -j MASQUERADE
|
|
||||||
|
|
||||||
# Full access from VPN clients.
|
|
||||||
iptables -I INPUT -j ACCEPT -s ${cfg.vpn.clients} -d ${internal}
|
|
||||||
iptables -I INPUT -j ACCEPT -s ${cfg.frkn.address} -d ${internal}
|
|
||||||
|
|
||||||
# Full access from Lan.
|
# Full access from Lan.
|
||||||
iptables -I INPUT -j ACCEPT -i ${lan} -d ${internal}
|
iptables -I INPUT -j ACCEPT -i ${lan} -d ${internal}
|
||||||
|
@ -187,52 +173,29 @@ in {
|
||||||
|
|
||||||
# Allow DHCP.
|
# Allow DHCP.
|
||||||
iptables -I INPUT -j ACCEPT -i ${lan} -p udp --dport 67
|
iptables -I INPUT -j ACCEPT -i ${lan} -p udp --dport 67
|
||||||
'')
|
|
||||||
# Expose DNS server for internal network.
|
|
||||||
+ (mkForward internal cfg.dns.port cfg.dns.address cfg.dns.port tcp)
|
|
||||||
+ (mkForward internal cfg.dns.port cfg.dns.address cfg.dns.port udp)
|
|
||||||
|
|
||||||
# Email server.
|
# Public email server.
|
||||||
+ (mkForward external 25 cfg.mail.address 25 tcp)
|
ip46tables -I INPUT -j ACCEPT -i ${wan} -p tcp --dport 25
|
||||||
+ (mkForward internal 25 cfg.mail.address 25 tcp)
|
|
||||||
+ (mkForward internal 465 cfg.mail.address 465 tcp)
|
|
||||||
+ (mkForward internal 993 cfg.mail.address 993 tcp)
|
|
||||||
|
|
||||||
# FRKN internal proxy server.
|
# Public VPN service.
|
||||||
+ (mkForward internal cfg.frkn.port cfg.frkn.address cfg.frkn.port tcp)
|
ip46tables -I INPUT -j ACCEPT -i ${wan} -p udp --dport 22145
|
||||||
+ (mkForward internal cfg.frkn.torport cfg.frkn.address cfg.frkn.torport tcp)
|
iptables -I INPUT -j ACCEPT -s 10.0.1.0/24 -d ${internal}
|
||||||
+ (mkForward internal cfg.frkn.xrayport cfg.frkn.address cfg.frkn.xrayport tcp)
|
|
||||||
+ (mkForward internal cfg.frkn.port cfg.frkn.address cfg.frkn.port udp)
|
|
||||||
+ (mkForward internal cfg.frkn.torport cfg.frkn.address cfg.frkn.torport udp)
|
|
||||||
+ (mkForward internal cfg.frkn.xrayport cfg.frkn.address cfg.frkn.xrayport udp)
|
|
||||||
|
|
||||||
# VPN connections.
|
# Public Nginx.
|
||||||
+ (mkForward external cfg.vpn.port cfg.vpn.address cfg.vpn.port udp)
|
ip46tables -I INPUT -j ACCEPT -i ${wan} -p tcp --dport 443
|
||||||
|
|
||||||
# Nginx HTTP.
|
# Deluge torrenting ports.
|
||||||
+ (mkForward external cfg.proxy.port cfg.proxy.address cfg.proxy.port tcp)
|
ip46tables -I INPUT -j ACCEPT -i ${wan} -p tcp --dport 54630
|
||||||
+ (mkForward internal cfg.proxy.port cfg.proxy.address cfg.proxy.port tcp)
|
ip46tables -I INPUT -j ACCEPT -i ${wan} -p udp --dport 54630
|
||||||
|
ip46tables -I INPUT -j ACCEPT -i ${wan} -p tcp --dport 54631
|
||||||
# Download ports for torrents.
|
ip46tables -I INPUT -j ACCEPT -i ${wan} -p udp --dport 54631
|
||||||
+ (mkForward external 54630 cfg.download.address 54630 tcp)
|
|
||||||
+ (mkForward external 54631 cfg.download.address 54631 tcp)
|
|
||||||
+ (mkForward external 54630 cfg.download.address 54630 udp)
|
|
||||||
+ (mkForward external 54631 cfg.download.address 54631 udp)
|
|
||||||
|
|
||||||
# Git SSH connections.
|
|
||||||
+ (mkForward external cfg.git.portSsh cfg.git.address cfg.git.portSsh tcp)
|
|
||||||
+ (mkForward internal cfg.git.portSsh cfg.git.address cfg.git.portSsh tcp)
|
|
||||||
|
|
||||||
# Print serivce.
|
|
||||||
+ (mkForward internal cfg.print.port cfg.print.address cfg.print.port tcp)
|
|
||||||
|
|
||||||
# Terraria server.
|
# Terraria server.
|
||||||
+ (mkForward external cfg.terraria.port cfg.terraria.address cfg.terraria.port tcp)
|
ip46tables -I INPUT -j ACCEPT -i ${wan} -p tcp --dport 22777
|
||||||
+ (mkForward internal cfg.terraria.port cfg.terraria.address cfg.terraria.port tcp)
|
|
||||||
|
|
||||||
# SSH access from WAN.
|
# Public SSH access.
|
||||||
# + (mkForward external 22143 config.container.host 22143 tcp)
|
# ip46tables -I INPUT -j ACCEPT -i ${wan} -p tcp --dport 22143
|
||||||
;
|
'';
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
38
host/x86_64-linux/home/Nextcloud.nix
Normal file
38
host/x86_64-linux/home/Nextcloud.nix
Normal file
|
@ -0,0 +1,38 @@
|
||||||
|
{
|
||||||
|
config,
|
||||||
|
pkgs,
|
||||||
|
...
|
||||||
|
}: {
|
||||||
|
services.nextcloud = {
|
||||||
|
enable = true;
|
||||||
|
database.createLocally = true;
|
||||||
|
extraAppsEnable = true;
|
||||||
|
hostName = "cloud.voronind.com";
|
||||||
|
https = true;
|
||||||
|
# package = pkgs.nextcloud29;
|
||||||
|
# phpOptions = {
|
||||||
|
# memory_limit = lib.mkForce "20G";
|
||||||
|
# };
|
||||||
|
config = {
|
||||||
|
adminpassFile = "${pkgs.writeText "NextcloudPassword" "root"}";
|
||||||
|
adminuser = "root";
|
||||||
|
dbname = "nextcloud";
|
||||||
|
# dbpassFile = "${pkgs.writeText "NextcloudDbPassword" "nextcloud"}";
|
||||||
|
dbtype = "pgsql";
|
||||||
|
dbuser = "nextcloud";
|
||||||
|
};
|
||||||
|
extraApps = {
|
||||||
|
inherit (config.services.nextcloud.package.packages.apps)
|
||||||
|
contacts calendar onlyoffice;
|
||||||
|
};
|
||||||
|
settings = {
|
||||||
|
allow_local_remote_servers = true;
|
||||||
|
trusted_domains = [
|
||||||
|
"cloud.voronind.com"
|
||||||
|
];
|
||||||
|
trusted_proxies = [
|
||||||
|
# proxy.address
|
||||||
|
];
|
||||||
|
};
|
||||||
|
};
|
||||||
|
}
|
50
host/x86_64-linux/home/Nginx.nix
Normal file
50
host/x86_64-linux/home/Nginx.nix
Normal file
|
@ -0,0 +1,50 @@
|
||||||
|
# NOTE: To generate self-signed certs use: `openssl req -x509 -nodes -days 365 -newkey rsa:2048 -keyout ./privkey.pem -out ./fullchain.pem`
|
||||||
|
# For dhparams: `openssl dhparam -out ./ssl-dhparam.pem 4096`
|
||||||
|
# Example for options-ssl-nginx.conf:
|
||||||
|
# ```
|
||||||
|
# ssl_session_cache shared:le_nginx_SSL:10m;
|
||||||
|
# ssl_session_timeout 1440m;
|
||||||
|
# ssl_protocols TLSv1.2 TLSv1.3;
|
||||||
|
# ssl_prefer_server_ciphers off;
|
||||||
|
# ssl_ciphers "ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-CHACHA20-POLY1305:ECDHE-RSA-CHACHA20-POLY1305:DHE-RSA-AES128-GCM-SHA256:DHE-RSA-AES256-GCM-SHA384";
|
||||||
|
# ```
|
||||||
|
# For certbot to generate new keys: `certbot certonly --manual --manual-public-ip-logging-ok --preferred-challenges dns-01 --server https://acme-v02.api.letsencrypt.org/directory -d "*.voronind.com" -d voronind.com`
|
||||||
|
{
|
||||||
|
pkgs,
|
||||||
|
util,
|
||||||
|
...
|
||||||
|
} @args: let
|
||||||
|
virtualHosts = util.catSet (util.ls ./nginx) args;
|
||||||
|
in {
|
||||||
|
environment.systemPackages = with pkgs; [ certbot ];
|
||||||
|
|
||||||
|
services.nginx = {
|
||||||
|
inherit virtualHosts;
|
||||||
|
enable = true;
|
||||||
|
clientMaxBodySize = "4096m";
|
||||||
|
recommendedOptimisation = true;
|
||||||
|
recommendedProxySettings = true;
|
||||||
|
appendConfig = util.trimTabs ''
|
||||||
|
worker_processes 4;
|
||||||
|
'';
|
||||||
|
eventsConfig = util.trimTabs ''
|
||||||
|
worker_connections 4096;
|
||||||
|
'';
|
||||||
|
appendHttpConfig = util.trimTabs ''
|
||||||
|
proxy_max_temp_file_size 0;
|
||||||
|
proxy_buffering off;
|
||||||
|
|
||||||
|
server {
|
||||||
|
listen 443 ssl default_server;
|
||||||
|
server_name _;
|
||||||
|
|
||||||
|
ssl_certificate /etc/letsencrypt/live/voronind.com/fullchain.pem;
|
||||||
|
ssl_certificate_key /etc/letsencrypt/live/voronind.com/privkey.pem;
|
||||||
|
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
||||||
|
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
||||||
|
|
||||||
|
return 403;
|
||||||
|
}
|
||||||
|
'';
|
||||||
|
};
|
||||||
|
}
|
20
host/x86_64-linux/home/OnlyOffice.nix
Normal file
20
host/x86_64-linux/home/OnlyOffice.nix
Normal file
|
@ -0,0 +1,20 @@
|
||||||
|
# NOTE: Imperative part:
|
||||||
|
# 1. You need to change PSQL tables owner from root to onlyoffice, too. They don't do that automatically for some reason.
|
||||||
|
# 2. TODO: Generate JWT secret at /var/lib/onlyoffice/jwt, i.e. 9wLfMGha1YrfvWpb5hyYjZf8pvJQ3swS
|
||||||
|
# SEE: https://git.voronind.com/voronind/nixos/issues/74
|
||||||
|
{
|
||||||
|
config,
|
||||||
|
lib,
|
||||||
|
...
|
||||||
|
}: {
|
||||||
|
# services.onlyoffice = {
|
||||||
|
# enable = true;
|
||||||
|
# hostname = "office.voronind.com";
|
||||||
|
# jwtSecretFile = "/var/www/onlyoffice/jwt";
|
||||||
|
#
|
||||||
|
# postgresName = "onlyoffice";
|
||||||
|
# postgresUser = "onlyoffice";
|
||||||
|
# # postgresPasswordFile = "${pkgs.writeText "OfficeDbPassword" dbName}";
|
||||||
|
# # rabbitmqUrl = "amqp://guest:guest@${config.container.module.rabbitmq.address}:${toString config.container.module.rabbitmq.port}";
|
||||||
|
# };
|
||||||
|
}
|
62
host/x86_64-linux/home/Ovpn.nix
Normal file
62
host/x86_64-linux/home/Ovpn.nix
Normal file
|
@ -0,0 +1,62 @@
|
||||||
|
# easyrsa --days=36500 init-pki
|
||||||
|
# easyrsa --days=36500 build-ca
|
||||||
|
# easyrsa --days=36500 build-server-full <SERVER_NAME> nopass
|
||||||
|
# easyrsa --days=36500 build-client-full <CLIENT_NAME> nopass
|
||||||
|
# easyrsa gen-crl
|
||||||
|
# openssl dhparam -out dh2048.pem 2048
|
||||||
|
# Don't forget to set tls hostname on the client to match SERVER_NAME *AND* disable ipv6 ?
|
||||||
|
|
||||||
|
# easyrsa revoke <CLIENT_NAME>
|
||||||
|
# easyrsa gen-crl
|
||||||
|
# restart container
|
||||||
|
|
||||||
|
# SEE: https://github.com/OpenVPN/openvpn/blob/master/sample/sample-config-files/server.conf
|
||||||
|
# SRC: https://github.com/TinCanTech/easy-tls
|
||||||
|
{
|
||||||
|
pkgs,
|
||||||
|
util,
|
||||||
|
...
|
||||||
|
}: {
|
||||||
|
environment.systemPackages = with pkgs; [
|
||||||
|
easyrsa
|
||||||
|
openvpn
|
||||||
|
];
|
||||||
|
|
||||||
|
users = {
|
||||||
|
groups.openvpn = {};
|
||||||
|
users.openvpn = {
|
||||||
|
group = "openvpn";
|
||||||
|
isSystemUser = true;
|
||||||
|
# uid = 1000;
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
# NOTE: Change the `server` to match `cfg.clients` or write a substring here.
|
||||||
|
services.openvpn.servers.vpn = {
|
||||||
|
autoStart = true;
|
||||||
|
config = util.trimTabs ''
|
||||||
|
ca /var/lib/ovpn/pki/ca.crt
|
||||||
|
cert /var/lib/ovpn/pki/issued/home.crt
|
||||||
|
client-to-client
|
||||||
|
crl-verify /var/lib/ovpn/pki/crl.pem
|
||||||
|
dev tun
|
||||||
|
dh /var/lib/ovpn/dh2048.pem
|
||||||
|
explicit-exit-notify 1
|
||||||
|
group openvpn
|
||||||
|
ifconfig-pool-persist ipp.txt
|
||||||
|
keepalive 10 120
|
||||||
|
key /var/lib/ovpn/pki/private/home.key
|
||||||
|
persist-tun
|
||||||
|
port 22145
|
||||||
|
proto udp
|
||||||
|
push "dhcp-option DNS 10.0.0.1"
|
||||||
|
push "dhcp-option DNS 10.0.0.1"
|
||||||
|
push "route 10.0.0.0 255.0.0.0"
|
||||||
|
server 10.0.1.0 255.255.255.0
|
||||||
|
status openvpn-status.log
|
||||||
|
topology subnet
|
||||||
|
user openvpn
|
||||||
|
verb 4
|
||||||
|
'';
|
||||||
|
};
|
||||||
|
}
|
24
host/x86_64-linux/home/Paperless.nix
Normal file
24
host/x86_64-linux/home/Paperless.nix
Normal file
|
@ -0,0 +1,24 @@
|
||||||
|
{
|
||||||
|
lib,
|
||||||
|
pkgs,
|
||||||
|
...
|
||||||
|
}: {
|
||||||
|
services.paperless = {
|
||||||
|
enable = true;
|
||||||
|
address = "0.0.0.0";
|
||||||
|
dataDir = "/var/lib/paperless";
|
||||||
|
# port = cfg.port;
|
||||||
|
passwordFile = pkgs.writeText "PaperlessPassword" "root"; # NOTE: Only for initial setup, change later.
|
||||||
|
settings = {
|
||||||
|
PAPERLESS_ADMIN_USER = "root";
|
||||||
|
PAPERLESS_DBHOST = "/run/postgresql";
|
||||||
|
PAPERLESS_DBENGINE = "postgresql";
|
||||||
|
PAPERLESS_DBNAME = "paperless";
|
||||||
|
PAPERLESS_DBPASS = "paperless";
|
||||||
|
PAPERLESS_DBUSER = "paperless";
|
||||||
|
PAPERLESS_OCR_LANGUAGE = "rus";
|
||||||
|
# PAPERLESS_REDIS = "redis://${config.container.module.redis.address}:${toString config.container.module.redis.port}";
|
||||||
|
PAPERLESS_URL = "https://paper.voronind.com";
|
||||||
|
};
|
||||||
|
};
|
||||||
|
}
|
48
host/x86_64-linux/home/Postgres.nix
Normal file
48
host/x86_64-linux/home/Postgres.nix
Normal file
|
@ -0,0 +1,48 @@
|
||||||
|
{
|
||||||
|
config,
|
||||||
|
lib,
|
||||||
|
pkgs,
|
||||||
|
...
|
||||||
|
}: {
|
||||||
|
services.postgresql = let
|
||||||
|
# Populate with services here.
|
||||||
|
configurations = [
|
||||||
|
"forgejo"
|
||||||
|
"invidious"
|
||||||
|
"mattermost"
|
||||||
|
"nextcloud"
|
||||||
|
"onlyoffice"
|
||||||
|
"paperless"
|
||||||
|
"privatebin"
|
||||||
|
];
|
||||||
|
|
||||||
|
ensureDatabases = [ "root" ] ++ configurations;
|
||||||
|
|
||||||
|
ensureUsers = map (name: {
|
||||||
|
inherit name;
|
||||||
|
ensureDBOwnership = true;
|
||||||
|
ensureClauses = if name == "root" then {
|
||||||
|
createdb = true;
|
||||||
|
createrole = true;
|
||||||
|
superuser = true;
|
||||||
|
} else { };
|
||||||
|
}) ensureDatabases;
|
||||||
|
|
||||||
|
authentication = "local all all trust";
|
||||||
|
in {
|
||||||
|
inherit authentication ensureDatabases ensureUsers;
|
||||||
|
|
||||||
|
enable = true;
|
||||||
|
dataDir = "/var/lib/postgresql/14";
|
||||||
|
package = pkgs.postgresql_14;
|
||||||
|
|
||||||
|
# NOTE: Debug mode.
|
||||||
|
# settings = {
|
||||||
|
# log_connections = true;
|
||||||
|
# log_destination = lib.mkForce "syslog";
|
||||||
|
# log_disconnections = true;
|
||||||
|
# log_statement = "all";
|
||||||
|
# logging_collector = true;
|
||||||
|
# };
|
||||||
|
};
|
||||||
|
}
|
45
host/x86_64-linux/home/Privatebin.nix
Normal file
45
host/x86_64-linux/home/Privatebin.nix
Normal file
|
@ -0,0 +1,45 @@
|
||||||
|
{
|
||||||
|
__findFile,
|
||||||
|
pkgs,
|
||||||
|
...
|
||||||
|
} @args: let
|
||||||
|
package = (pkgs.callPackage <package/privatebin> args);
|
||||||
|
in {
|
||||||
|
environment.systemPackages = [ package ];
|
||||||
|
systemd.packages = [ package ];
|
||||||
|
|
||||||
|
users.users.paste = {
|
||||||
|
group = "nginx";
|
||||||
|
isSystemUser = true;
|
||||||
|
};
|
||||||
|
|
||||||
|
services = {
|
||||||
|
phpfpm.pools.paste = {
|
||||||
|
group = "nginx";
|
||||||
|
user = "paste";
|
||||||
|
phpPackage = pkgs.php;
|
||||||
|
settings = {
|
||||||
|
"catch_workers_output" = true;
|
||||||
|
"listen.owner" = "nginx";
|
||||||
|
"php_admin_flag[log_errors]" = true;
|
||||||
|
"php_admin_value[error_log]" = "stderr";
|
||||||
|
"pm" = "dynamic";
|
||||||
|
"pm.max_children" = "32";
|
||||||
|
"pm.max_requests" = "500";
|
||||||
|
"pm.max_spare_servers" = "4";
|
||||||
|
"pm.min_spare_servers" = "2";
|
||||||
|
"pm.start_servers" = "2";
|
||||||
|
};
|
||||||
|
phpEnv = {
|
||||||
|
# CONFIG_PATH = "${package}/cfg"; # NOTE: Not working?
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
nginx = {
|
||||||
|
enable = true;
|
||||||
|
virtualHosts."paste.voronind.com" = {
|
||||||
|
root = "${package}";
|
||||||
|
};
|
||||||
|
};
|
||||||
|
};
|
||||||
|
}
|
8
host/x86_64-linux/home/Rabbitmq.nix
Normal file
8
host/x86_64-linux/home/Rabbitmq.nix
Normal file
|
@ -0,0 +1,8 @@
|
||||||
|
{ ... }: {
|
||||||
|
services.rabbitmq = {
|
||||||
|
enable = true;
|
||||||
|
# configItems = {
|
||||||
|
# "loopback_users" = "none";
|
||||||
|
# };
|
||||||
|
};
|
||||||
|
}
|
9
host/x86_64-linux/home/Redis.nix
Normal file
9
host/x86_64-linux/home/Redis.nix
Normal file
|
@ -0,0 +1,9 @@
|
||||||
|
{ ... }: {
|
||||||
|
services.redis.servers.main = {
|
||||||
|
enable = true;
|
||||||
|
# port = cfg.port;
|
||||||
|
# extraParams = [
|
||||||
|
# "--protected-mode no"
|
||||||
|
# ];
|
||||||
|
};
|
||||||
|
}
|
108
host/x86_64-linux/home/SearX.nix
Normal file
108
host/x86_64-linux/home/SearX.nix
Normal file
|
@ -0,0 +1,108 @@
|
||||||
|
{
|
||||||
|
config,
|
||||||
|
pkgs,
|
||||||
|
...
|
||||||
|
}: {
|
||||||
|
services.searx = {
|
||||||
|
enable = true;
|
||||||
|
package = pkgs.searxng;
|
||||||
|
# REF: https://github.com/searxng/searxng/blob/master/searx/settings.yml
|
||||||
|
settings = {
|
||||||
|
general = {
|
||||||
|
debug = false;
|
||||||
|
enable_metrics = false;
|
||||||
|
instance_name = "SearX";
|
||||||
|
};
|
||||||
|
server = {
|
||||||
|
# bind_address = cfg.address;
|
||||||
|
image_proxy = false;
|
||||||
|
limiter = false;
|
||||||
|
method = "GET";
|
||||||
|
port = 34972;
|
||||||
|
public_instance = false;
|
||||||
|
secret_key = "searxxx";
|
||||||
|
};
|
||||||
|
search = {
|
||||||
|
autocomplete = "";
|
||||||
|
autocomplete_min = 4;
|
||||||
|
default_lang = "auto";
|
||||||
|
safe_search = 0;
|
||||||
|
};
|
||||||
|
ui = {
|
||||||
|
center_alignment = false;
|
||||||
|
default_locale = "";
|
||||||
|
default_theme = "simple";
|
||||||
|
hotkeys = "vim";
|
||||||
|
infinite_scroll = false;
|
||||||
|
simple_style = "dark";
|
||||||
|
};
|
||||||
|
outgoing = {
|
||||||
|
enable_http2 = true;
|
||||||
|
max_request_timeout = 10.0;
|
||||||
|
pool_connections = 100;
|
||||||
|
pool_maxsize = 20;
|
||||||
|
request_timeout = 3.0;
|
||||||
|
# proxies = {
|
||||||
|
# "all://" = with config.container.module; [
|
||||||
|
# # "socks5:${frkn.address}:${frkn.port}"
|
||||||
|
# "socks5:${frkn.address}:1081"
|
||||||
|
# # "socks5:${frkn.address}:9150"
|
||||||
|
# ];
|
||||||
|
# };
|
||||||
|
# using_tor_proxy = true;
|
||||||
|
# extra_proxy_timeout = 10;
|
||||||
|
};
|
||||||
|
# plugins = [ ];
|
||||||
|
enabled_plugins = [
|
||||||
|
"Basic Calculator"
|
||||||
|
"Hostnames plugin"
|
||||||
|
"Tracker URL remover"
|
||||||
|
];
|
||||||
|
hostnames = {
|
||||||
|
replace = {
|
||||||
|
"(.*\.)?youtu\.be$" = "yt.voronind.com";
|
||||||
|
"(.*\.)?youtube\.com$" = "yt.voronind.com";
|
||||||
|
};
|
||||||
|
remove = [
|
||||||
|
"(.*\.)?dzen\.ru$"
|
||||||
|
"(.*\.)?facebook.com$"
|
||||||
|
"(.*\.)?gosuslugi\.ru$"
|
||||||
|
"(.*\.)?quora\.com$"
|
||||||
|
"(.*\.)?rutube\.ru$"
|
||||||
|
"(.*\.)?vk\.com$"
|
||||||
|
];
|
||||||
|
low_priority = [
|
||||||
|
"(.*\.)?google(\..*)?$"
|
||||||
|
"(.*\.)?microsoft\.com$"
|
||||||
|
];
|
||||||
|
high_priority = [
|
||||||
|
"(.*\.)?4pda.to$"
|
||||||
|
"(.*\.)?github.com$"
|
||||||
|
"(.*\.)?wikipedia.org$"
|
||||||
|
];
|
||||||
|
};
|
||||||
|
categories_as_tabs = {
|
||||||
|
files = { };
|
||||||
|
general = { };
|
||||||
|
images = { };
|
||||||
|
it = { };
|
||||||
|
map = { };
|
||||||
|
news = { };
|
||||||
|
videos = { };
|
||||||
|
};
|
||||||
|
engines = let
|
||||||
|
mkEnable = name: {
|
||||||
|
inherit name;
|
||||||
|
disabled = false;
|
||||||
|
};
|
||||||
|
mkDisable = name: {
|
||||||
|
inherit name;
|
||||||
|
disabled = true;
|
||||||
|
};
|
||||||
|
in [
|
||||||
|
(mkEnable "bing")
|
||||||
|
(mkDisable "qwant")
|
||||||
|
];
|
||||||
|
};
|
||||||
|
};
|
||||||
|
}
|
20
host/x86_64-linux/home/Terraria.nix
Normal file
20
host/x86_64-linux/home/Terraria.nix
Normal file
|
@ -0,0 +1,20 @@
|
||||||
|
{
|
||||||
|
pkgs,
|
||||||
|
...
|
||||||
|
}: {
|
||||||
|
# NOTE: Admin with `tmux -S /var/lib/terraria/terraria.sock attach-session -t 0`
|
||||||
|
environment.systemPackages = with pkgs; [ tmux ];
|
||||||
|
|
||||||
|
services.terraria = {
|
||||||
|
enable = true;
|
||||||
|
autoCreatedWorldSize = "large";
|
||||||
|
messageOfTheDay = "<3";
|
||||||
|
maxPlayers = 4;
|
||||||
|
noUPnP = false;
|
||||||
|
openFirewall = false;
|
||||||
|
password = "mishadima143";
|
||||||
|
port = 22777;
|
||||||
|
secure = false;
|
||||||
|
worldPath = "/var/lib/terraria/.local/share/Terraria/Worlds/World.wld";
|
||||||
|
};
|
||||||
|
}
|
19
host/x86_64-linux/home/UptimeKuma.nix
Normal file
19
host/x86_64-linux/home/UptimeKuma.nix
Normal file
|
@ -0,0 +1,19 @@
|
||||||
|
{
|
||||||
|
lib,
|
||||||
|
...
|
||||||
|
}: {
|
||||||
|
services.uptime-kuma = {
|
||||||
|
enable = true;
|
||||||
|
settings = {
|
||||||
|
DATA_DIR = "/var/lib/uptime-kuma/";
|
||||||
|
PORT = "64901";
|
||||||
|
# HOST = cfg.address;
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
systemd.services.uptime-kuma = {
|
||||||
|
serviceConfig = {
|
||||||
|
DynamicUser = lib.mkForce false;
|
||||||
|
};
|
||||||
|
};
|
||||||
|
}
|
15
host/x86_64-linux/home/Vaultwarden.nix
Normal file
15
host/x86_64-linux/home/Vaultwarden.nix
Normal file
|
@ -0,0 +1,15 @@
|
||||||
|
{ ... }: {
|
||||||
|
services.vaultwarden = {
|
||||||
|
enable = true;
|
||||||
|
dbBackend = "sqlite";
|
||||||
|
environmentFile = "/var/lib/vaultwarden/Env";
|
||||||
|
config = {
|
||||||
|
DATA_FOLDER = "/var/lib/vaultwarden";
|
||||||
|
DOMAIN = "https://pass.voronind.com";
|
||||||
|
# ROCKET_ADDRESS = cfg.address;
|
||||||
|
ROCKET_PORT = 8001;
|
||||||
|
SIGNUPS_ALLOWED = false;
|
||||||
|
WEB_VAULT_ENABLED = true;
|
||||||
|
};
|
||||||
|
};
|
||||||
|
}
|
20
host/x86_64-linux/home/nginx/Camera.nix
Normal file
20
host/x86_64-linux/home/nginx/Camera.nix
Normal file
|
@ -0,0 +1,20 @@
|
||||||
|
{
|
||||||
|
util,
|
||||||
|
...
|
||||||
|
}: {
|
||||||
|
"camera.voronind.com".extraConfig = util.trimTabs ''
|
||||||
|
listen 443 ssl;
|
||||||
|
|
||||||
|
location / {
|
||||||
|
allow 10.0.0.0/8;
|
||||||
|
allow fd09:8d46:b26::/48;
|
||||||
|
deny all;
|
||||||
|
return 301 rtsp://10.0.0.12:554/live/main;
|
||||||
|
}
|
||||||
|
|
||||||
|
ssl_certificate /etc/letsencrypt/live/voronind.com/fullchain.pem;
|
||||||
|
ssl_certificate_key /etc/letsencrypt/live/voronind.com/privkey.pem;
|
||||||
|
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
||||||
|
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
||||||
|
'';
|
||||||
|
}
|
23
host/x86_64-linux/home/nginx/Change.nix
Normal file
23
host/x86_64-linux/home/nginx/Change.nix
Normal file
|
@ -0,0 +1,23 @@
|
||||||
|
{
|
||||||
|
util,
|
||||||
|
...
|
||||||
|
}: {
|
||||||
|
"change.voronind.com".extraConfig = util.trimTabs ''
|
||||||
|
listen 443 ssl;
|
||||||
|
|
||||||
|
location / {
|
||||||
|
allow 10.0.0.0/8;
|
||||||
|
allow fd09:8d46:b26::/48;
|
||||||
|
deny all;
|
||||||
|
|
||||||
|
proxy_pass http://127.0.0.1:5001$request_uri;
|
||||||
|
|
||||||
|
add_header Referrer-Policy 'origin';
|
||||||
|
}
|
||||||
|
|
||||||
|
ssl_certificate /etc/letsencrypt/live/voronind.com/fullchain.pem;
|
||||||
|
ssl_certificate_key /etc/letsencrypt/live/voronind.com/privkey.pem;
|
||||||
|
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
||||||
|
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
||||||
|
'';
|
||||||
|
}
|
25
host/x86_64-linux/home/nginx/Cups.nix
Normal file
25
host/x86_64-linux/home/nginx/Cups.nix
Normal file
|
@ -0,0 +1,25 @@
|
||||||
|
{
|
||||||
|
util,
|
||||||
|
...
|
||||||
|
}: {
|
||||||
|
"print.voronind.com".extraConfig = util.trimTabs ''
|
||||||
|
listen 443 ssl;
|
||||||
|
|
||||||
|
location / {
|
||||||
|
allow 10.0.0.0/8;
|
||||||
|
allow fd09:8d46:b26::/48;
|
||||||
|
deny all;
|
||||||
|
|
||||||
|
proxy_pass http://127.0.0.1:631$request_uri;
|
||||||
|
|
||||||
|
proxy_set_header Host "127.0.0.1";
|
||||||
|
proxy_set_header X-Real-IP $remote_addr;
|
||||||
|
proxy_set_header X-Forward-For $proxy_add_x_forwarded_for;
|
||||||
|
}
|
||||||
|
|
||||||
|
ssl_certificate /etc/letsencrypt/live/voronind.com/fullchain.pem;
|
||||||
|
ssl_certificate_key /etc/letsencrypt/live/voronind.com/privkey.pem;
|
||||||
|
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
||||||
|
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
||||||
|
'';
|
||||||
|
}
|
20
host/x86_64-linux/home/nginx/Deluge.nix
Normal file
20
host/x86_64-linux/home/nginx/Deluge.nix
Normal file
|
@ -0,0 +1,20 @@
|
||||||
|
{
|
||||||
|
util,
|
||||||
|
...
|
||||||
|
}: {
|
||||||
|
"download.voronind.com".extraConfig = util.trimTabs ''
|
||||||
|
listen 443 ssl;
|
||||||
|
|
||||||
|
location / {
|
||||||
|
allow 10.0.0.0/8;
|
||||||
|
allow fd09:8d46:b26::/48;
|
||||||
|
deny all;
|
||||||
|
proxy_pass http://127.0.0.1:8112$request_uri;
|
||||||
|
}
|
||||||
|
|
||||||
|
ssl_certificate /etc/letsencrypt/live/voronind.com/fullchain.pem;
|
||||||
|
ssl_certificate_key /etc/letsencrypt/live/voronind.com/privkey.pem;
|
||||||
|
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
||||||
|
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
||||||
|
'';
|
||||||
|
}
|
24
host/x86_64-linux/home/nginx/Forgejo.nix
Normal file
24
host/x86_64-linux/home/nginx/Forgejo.nix
Normal file
|
@ -0,0 +1,24 @@
|
||||||
|
{
|
||||||
|
util,
|
||||||
|
...
|
||||||
|
}: {
|
||||||
|
"git.voronind.com".extraConfig = util.trimTabs ''
|
||||||
|
listen 443 ssl;
|
||||||
|
|
||||||
|
location ~ ^/(admin|api|user) {
|
||||||
|
allow 10.0.0.0/8;
|
||||||
|
allow fd09:8d46:b26::/48;
|
||||||
|
deny all;
|
||||||
|
proxy_pass http://127.0.0.1:3000$request_uri;
|
||||||
|
}
|
||||||
|
|
||||||
|
location / {
|
||||||
|
proxy_pass http://127.0.0.1:3000$request_uri;
|
||||||
|
}
|
||||||
|
|
||||||
|
ssl_certificate /etc/letsencrypt/live/voronind.com/fullchain.pem;
|
||||||
|
ssl_certificate_key /etc/letsencrypt/live/voronind.com/privkey.pem;
|
||||||
|
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
||||||
|
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
||||||
|
'';
|
||||||
|
}
|
30
host/x86_64-linux/home/nginx/Grocy.nix
Normal file
30
host/x86_64-linux/home/nginx/Grocy.nix
Normal file
|
@ -0,0 +1,30 @@
|
||||||
|
{
|
||||||
|
config,
|
||||||
|
lib,
|
||||||
|
util,
|
||||||
|
...
|
||||||
|
}: {
|
||||||
|
"stock.voronind.com" = {
|
||||||
|
locations."~ \\.php$".extraConfig = lib.mkForce (util.trimTabs ''
|
||||||
|
allow 10.0.0.0/8;
|
||||||
|
allow fd09:8d46:b26::/48;
|
||||||
|
deny all;
|
||||||
|
|
||||||
|
fastcgi_split_path_info ^(.+\.php)(/.+)$;
|
||||||
|
fastcgi_pass unix:${config.services.phpfpm.pools.grocy.socket};
|
||||||
|
include ${config.services.nginx.package}/conf/fastcgi.conf;
|
||||||
|
include ${config.services.nginx.package}/conf/fastcgi_params;
|
||||||
|
'');
|
||||||
|
|
||||||
|
extraConfig = lib.mkForce (util.trimTabs ''
|
||||||
|
listen 443 ssl;
|
||||||
|
|
||||||
|
ssl_certificate /etc/letsencrypt/live/voronind.com/fullchain.pem;
|
||||||
|
ssl_certificate_key /etc/letsencrypt/live/voronind.com/privkey.pem;
|
||||||
|
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
||||||
|
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
||||||
|
|
||||||
|
try_files $uri /index.php;
|
||||||
|
'');
|
||||||
|
};
|
||||||
|
}
|
27
host/x86_64-linux/home/nginx/Hass.nix
Normal file
27
host/x86_64-linux/home/nginx/Hass.nix
Normal file
|
@ -0,0 +1,27 @@
|
||||||
|
{
|
||||||
|
util,
|
||||||
|
...
|
||||||
|
}: {
|
||||||
|
"iot.voronind.com".extraConfig = util.trimTabs ''
|
||||||
|
listen 443 ssl;
|
||||||
|
|
||||||
|
location / {
|
||||||
|
allow 10.0.0.0/8;
|
||||||
|
allow fd09:8d46:b26::/48;
|
||||||
|
deny all;
|
||||||
|
|
||||||
|
# proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
|
||||||
|
proxy_set_header Host $host;
|
||||||
|
proxy_http_version 1.1;
|
||||||
|
proxy_set_header Upgrade $http_upgrade;
|
||||||
|
proxy_set_header Connection "upgrade";
|
||||||
|
|
||||||
|
proxy_pass http://127.0.0.1:8123$request_uri;
|
||||||
|
}
|
||||||
|
|
||||||
|
ssl_certificate /etc/letsencrypt/live/voronind.com/fullchain.pem;
|
||||||
|
ssl_certificate_key /etc/letsencrypt/live/voronind.com/privkey.pem;
|
||||||
|
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
||||||
|
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
||||||
|
'';
|
||||||
|
}
|
20
host/x86_64-linux/home/nginx/Homer.nix
Normal file
20
host/x86_64-linux/home/nginx/Homer.nix
Normal file
|
@ -0,0 +1,20 @@
|
||||||
|
{
|
||||||
|
util,
|
||||||
|
...
|
||||||
|
}: {
|
||||||
|
"home.voronind.com".extraConfig = util.trimTabs ''
|
||||||
|
listen 443 ssl;
|
||||||
|
|
||||||
|
location / {
|
||||||
|
allow 10.0.0.0/8;
|
||||||
|
allow fd09:8d46:b26::/48;
|
||||||
|
deny all;
|
||||||
|
try_files $uri $uri/index.html;
|
||||||
|
}
|
||||||
|
|
||||||
|
ssl_certificate /etc/letsencrypt/live/voronind.com/fullchain.pem;
|
||||||
|
ssl_certificate_key /etc/letsencrypt/live/voronind.com/privkey.pem;
|
||||||
|
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
||||||
|
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
||||||
|
'';
|
||||||
|
}
|
30
host/x86_64-linux/home/nginx/Invidious.nix
Normal file
30
host/x86_64-linux/home/nginx/Invidious.nix
Normal file
|
@ -0,0 +1,30 @@
|
||||||
|
{
|
||||||
|
util,
|
||||||
|
...
|
||||||
|
}: {
|
||||||
|
"yt.voronind.com".extraConfig = util.trimTabs ''
|
||||||
|
listen 443 ssl;
|
||||||
|
|
||||||
|
location / {
|
||||||
|
allow 10.0.0.0/8;
|
||||||
|
allow fd09:8d46:b26::/48;
|
||||||
|
deny all;
|
||||||
|
|
||||||
|
proxy_pass http://127.0.0.1:3001$request_uri;
|
||||||
|
|
||||||
|
proxy_set_header X-Forwarded-For $remote_addr;
|
||||||
|
proxy_set_header Host $host;
|
||||||
|
proxy_http_version 1.1;
|
||||||
|
proxy_set_header Connection "";
|
||||||
|
|
||||||
|
proxy_hide_header Content-Security-Policy;
|
||||||
|
proxy_hide_header X-Frame-Options;
|
||||||
|
proxy_hide_header X-Content-Type-Options;
|
||||||
|
}
|
||||||
|
|
||||||
|
ssl_certificate /etc/letsencrypt/live/voronind.com/fullchain.pem;
|
||||||
|
ssl_certificate_key /etc/letsencrypt/live/voronind.com/privkey.pem;
|
||||||
|
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
||||||
|
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
||||||
|
'';
|
||||||
|
}
|
20
host/x86_64-linux/home/nginx/Jellyfin.nix
Normal file
20
host/x86_64-linux/home/nginx/Jellyfin.nix
Normal file
|
@ -0,0 +1,20 @@
|
||||||
|
{
|
||||||
|
util,
|
||||||
|
...
|
||||||
|
}: {
|
||||||
|
"watch.voronind.com".extraConfig = util.trimTabs ''
|
||||||
|
listen 443 ssl;
|
||||||
|
|
||||||
|
location / {
|
||||||
|
allow 10.0.0.0/8;
|
||||||
|
allow fd09:8d46:b26::/48;
|
||||||
|
deny all;
|
||||||
|
proxy_pass http://127.0.0.1:8096$request_uri;
|
||||||
|
}
|
||||||
|
|
||||||
|
ssl_certificate /etc/letsencrypt/live/voronind.com/fullchain.pem;
|
||||||
|
ssl_certificate_key /etc/letsencrypt/live/voronind.com/privkey.pem;
|
||||||
|
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
||||||
|
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
||||||
|
'';
|
||||||
|
}
|
20
host/x86_64-linux/home/nginx/Kavita.nix
Normal file
20
host/x86_64-linux/home/nginx/Kavita.nix
Normal file
|
@ -0,0 +1,20 @@
|
||||||
|
{
|
||||||
|
util,
|
||||||
|
...
|
||||||
|
}: {
|
||||||
|
"read.voronind.com".extraConfig = util.trimTabs ''
|
||||||
|
listen 443 ssl;
|
||||||
|
|
||||||
|
location / {
|
||||||
|
allow 10.0.0.0/8;
|
||||||
|
allow fd09:8d46:b26::/48;
|
||||||
|
deny all;
|
||||||
|
proxy_pass http://127.0.0.1:5000$request_uri;
|
||||||
|
}
|
||||||
|
|
||||||
|
ssl_certificate /etc/letsencrypt/live/voronind.com/fullchain.pem;
|
||||||
|
ssl_certificate_key /etc/letsencrypt/live/voronind.com/privkey.pem;
|
||||||
|
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
||||||
|
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
||||||
|
'';
|
||||||
|
}
|
29
host/x86_64-linux/home/nginx/Mailserver.nix
Normal file
29
host/x86_64-linux/home/nginx/Mailserver.nix
Normal file
|
@ -0,0 +1,29 @@
|
||||||
|
{
|
||||||
|
config,
|
||||||
|
lib,
|
||||||
|
util,
|
||||||
|
...
|
||||||
|
}: {
|
||||||
|
"mail.voronind.com" = {
|
||||||
|
enableACME = false;
|
||||||
|
forceSSL = false;
|
||||||
|
locations."~* \\.php(/|$)".extraConfig = lib.mkForce (util.trimTabs ''
|
||||||
|
allow 10.0.0.0/8;
|
||||||
|
allow fd09:8d46:b26::/48;
|
||||||
|
deny all;
|
||||||
|
|
||||||
|
fastcgi_pass unix:${config.services.phpfpm.pools.roundcube.socket};
|
||||||
|
fastcgi_param PATH_INFO $fastcgi_path_info;
|
||||||
|
fastcgi_split_path_info ^(.+\.php)(/.+)$;
|
||||||
|
include ${config.services.nginx.package}/conf/fastcgi.conf;
|
||||||
|
'');
|
||||||
|
extraConfig = lib.mkForce (util.trimTabs ''
|
||||||
|
listen 443 ssl;
|
||||||
|
|
||||||
|
ssl_certificate /etc/letsencrypt/live/voronind.com/fullchain.pem;
|
||||||
|
ssl_certificate_key /etc/letsencrypt/live/voronind.com/privkey.pem;
|
||||||
|
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
||||||
|
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
||||||
|
'');
|
||||||
|
};
|
||||||
|
}
|
22
host/x86_64-linux/home/nginx/Nextcloud.nix
Normal file
22
host/x86_64-linux/home/nginx/Nextcloud.nix
Normal file
|
@ -0,0 +1,22 @@
|
||||||
|
{
|
||||||
|
util,
|
||||||
|
...
|
||||||
|
}: {
|
||||||
|
"cloud.voronind.com" = {
|
||||||
|
locations."~ ^/(settings/admin|settings/users|settings/apps|login|api)".extraConfig = util.trimTabs ''
|
||||||
|
allow 10.0.0.0/8;
|
||||||
|
allow fd09:8d46:b26::/48;
|
||||||
|
deny all;
|
||||||
|
try_files $uri $uri/ /index.php$request_uri;
|
||||||
|
'';
|
||||||
|
|
||||||
|
extraConfig = util.trimTabs ''
|
||||||
|
listen 443 ssl;
|
||||||
|
|
||||||
|
ssl_certificate /etc/letsencrypt/live/voronind.com/fullchain.pem;
|
||||||
|
ssl_certificate_key /etc/letsencrypt/live/voronind.com/privkey.pem;
|
||||||
|
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
||||||
|
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
||||||
|
'';
|
||||||
|
};
|
||||||
|
}
|
21
host/x86_64-linux/home/nginx/OnlyOffice.nix
Normal file
21
host/x86_64-linux/home/nginx/OnlyOffice.nix
Normal file
|
@ -0,0 +1,21 @@
|
||||||
|
{
|
||||||
|
lib,
|
||||||
|
util,
|
||||||
|
...
|
||||||
|
}: {
|
||||||
|
"office.voronind.com" = {
|
||||||
|
locations."/".extraConfig = lib.mkForce (util.trimTabs ''
|
||||||
|
add_header X-Forwarded-Proto https;
|
||||||
|
proxy_pass http://127.0.0.1:8000$request_uri;
|
||||||
|
'');
|
||||||
|
|
||||||
|
extraConfig = util.trimTabs ''
|
||||||
|
listen 443 ssl;
|
||||||
|
|
||||||
|
ssl_certificate /etc/letsencrypt/live/voronind.com/fullchain.pem;
|
||||||
|
ssl_certificate_key /etc/letsencrypt/live/voronind.com/privkey.pem;
|
||||||
|
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
||||||
|
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
||||||
|
'';
|
||||||
|
};
|
||||||
|
}
|
20
host/x86_64-linux/home/nginx/Paperless.nix
Normal file
20
host/x86_64-linux/home/nginx/Paperless.nix
Normal file
|
@ -0,0 +1,20 @@
|
||||||
|
{
|
||||||
|
util,
|
||||||
|
...
|
||||||
|
}: {
|
||||||
|
"paper.voronind.com".extraConfig = util.trimTabs ''
|
||||||
|
listen 443 ssl;
|
||||||
|
|
||||||
|
location / {
|
||||||
|
allow 10.0.0.0/8;
|
||||||
|
allow fd09:8d46:b26::/48;
|
||||||
|
deny all;
|
||||||
|
proxy_pass http://127.0.0.1:28981$request_uri;
|
||||||
|
}
|
||||||
|
|
||||||
|
ssl_certificate /etc/letsencrypt/live/voronind.com/fullchain.pem;
|
||||||
|
ssl_certificate_key /etc/letsencrypt/live/voronind.com/privkey.pem;
|
||||||
|
include /etc/letsencrypt/conf/options-ssl-nginx.conf;
|
||||||
|
ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem;
|
||||||
|
'';
|
||||||
|
}
|
Some files were not shown because too many files have changed in this diff Show more
Loading…
Reference in a new issue