{ pkgs, lib, config, factsGenerator, components, inputs, ... }: # don't forget the database backup before upgrading # ------------------------------------------------- # https://docs.nextcloud.com/server/stable/admin_manual/maintenance/backup.html # https://docs.nextcloud.com/server/stable/admin_manual/maintenance/upgrade.html let # todo : let nextcloud run as media, this would make this part easier. nextcloudUid = config.ids.uids.transmission; nextcloudGid = config.ids.gids.transmission; nextcloudPort = 9080; nextcloudHostName = "nextcloud.ingolf-wagner.de"; phpPackage = pkgs.php73; nextcloudPackage = pkgs.nextcloud29; mySQLPackage = pkgs.mysql; in { networking.firewall.allowedTCPPorts = [ 80 443 ]; networking.firewall.allowedUDPPorts = [ 80 443 ]; healthchecks.http.nextcloud = { url = "https://nextcloud.ingolf-wagner.de/login"; expectedContent = "Login"; }; services.nginx = { enable = true; recommendedProxySettings = true; virtualHosts = { "${nextcloudHostName}" = { forceSSL = true; enableACME = true; locations = { "/" = { proxyPass = "http://localhost:${toString nextcloudPort}"; extraConfig = '' sub_filter "http://${nextcloudHostName}" "https://${nextcloudHostName}"; # used for view/edit office file via Office Online Server client_max_body_size 0; proxy_buffering off; # to download files bigger than 1GB ''; }; "= /.well-known/carddav" = { priority = 210; extraConfig = "return 301 $scheme://$host/remote.php/dav;"; }; "= /.well-known/caldav" = { priority = 210; extraConfig = "return 301 $scheme://$host/remote.php/dav;"; }; }; }; }; }; clan.core.facts.services.nextcloud_root = factsGenerator.password { service = "nextcloud"; name = "root"; }; clan.core.facts.services.nextcloud_database = factsGenerator.password { service = "nextcloud"; name = "database"; }; # Container Setup # =============== # # running: # * nextcloud (php) # * mysql containers.nextcloud = { bindMounts = { rootpassword = { hostPath = config.clan.core.facts.services.nextcloud_root.secret."nextcloud.root".path; mountPoint = "/run/secrets/nextcloud.root.intput"; isReadOnly = true; }; databasepassword = { hostPath = config.clan.core.facts.services.nextcloud_database.secret."nextcloud.database".path; mountPoint = "/run/secrets/nextcloud.database.input"; isReadOnly = true; }; share = { hostPath = config.services.syncthing.settings.folders.share.path; mountPoint = "/media/share"; isReadOnly = true; }; }; privateNetwork = false; autoStart = true; config = { config, lib, ... }: { nixpkgs.pkgs = pkgs; imports = [ "${components}/monitor/container.nix" inputs.nix-topology.nixosModules.default ]; system.stateVersion = "23.11"; services.logrotate.checkConfig = false; # because uid 3000 does not exist in here # Configuring nameservers for containers is currently broken. # Therefore in some cases internet connectivity can be broken inside the containers. # A temporary workaround is to manually write the /etc/nixos/resolv.conf file like this: #environment.etc."resolv.conf".text = "nameserver 8.8.8.8"; systemd.tmpfiles.settings.nextcloud = { "/run/secrets/nextcloud.root"."C+" = { user = "nextcloud"; group = "nextcloud"; mode = "400"; argument = "/run/secrets/nextcloud.root.input"; }; "/run/secrets/nextcloud.database"."C+" = { user = "nextcloud"; group = "nextcloud"; mode = "400"; argument = "/run/secrets/nextcloud.database.input"; }; }; users.users.nextcloud.uid = nextcloudUid; users.groups.nextcloud = { gid = nextcloudGid; members = [ "nextcloud" ]; }; services.nginx = { defaultListen = [ { addr = "0.0.0.0"; port = nextcloudPort; } ]; # Use recommended settings recommendedGzipSettings = lib.mkDefault true; recommendedOptimisation = lib.mkDefault true; recommendedProxySettings = lib.mkDefault true; recommendedTlsSettings = lib.mkDefault true; }; # nextcloud database # ================== # # set user password: # ----------------- # #> mysql # mysql> ALTER USER 'nextcloud'@'localhost' IDENTIFIED BY 'nextcloud-password'; # # recreate database: # ------------------ # mysql> DROP DATABASE nextcloud; # mysql> CREATE DATABASE nextcloud; # # migration: # ---------- # nextcloud-occ db:convert-type --all-apps mysql nextcloud 127.0.0.1 nextcloud # # 4-byte stuff: # ------------- # https://docs.nextcloud.com/server/18/admin_manual/configuration_database/mysql_4byte_support.html # if you do this don't forget --default-character-set=utf8mb4 for mysqldump services.mysql = { enable = true; package = mySQLPackage; # https://nixos.org/manual/nixos/stable/release-notes.html#sec-release-20.09-incompatibilities ensureDatabases = [ "nextcloud" ]; ensureUsers = [ { name = "nextcloud"; ensurePermissions = { "nextcloud.*" = "ALL PRIVILEGES"; }; } ]; settings.mysqld = { innodb_large_prefix = true; innodb_file_format = "barracuda"; innodb_file_per_table = 1; innodb_read_only_compressed = 0; }; }; # Backup database # --------------- services.mysqlBackup = { enable = true; databases = config.services.mysql.ensureDatabases; singleTransaction = true; }; systemd.services."mysql-backup".serviceConfig = { ExecStartPre = [ "+/run/current-system/sw/bin/nextcloud-occ maintenance:mode --on" ]; ExecStopPost = [ "+/run/current-system/sw/bin/nextcloud-occ maintenance:mode --off" ]; }; # in php services.phpfpm = { phpPackage = phpPackage; phpOptions = '' opcache.revalidate_freq = 10 ''; }; # nextcloud setup services.nextcloud = { enable = true; package = nextcloudPackage; autoUpdateApps.enable = true; hostName = nextcloudHostName; https = true; settings = { overwriteprotocol = "https"; default_phone_region = "DE"; loglevel = 2; }; config = { adminpassFile = "/run/secrets/nextcloud.root"; #overwriteProtocol = "https"; dbtype = "mysql"; dbpassFile = "/run/secrets/nextcloud.database"; dbhost = "localhost:3306"; }; }; }; }; }