1 { config, lib, options, pkgs, ... }:
6 cfg = config.services.gogs;
7 opt = options.services.gogs;
8 configFile = pkgs.writeText "app.ini" ''
9 APP_NAME = ${cfg.appName}
10 RUN_USER = ${cfg.user}
14 DB_TYPE = ${cfg.database.type}
15 HOST = ${cfg.database.host}:${toString cfg.database.port}
16 NAME = ${cfg.database.name}
17 USER = ${cfg.database.user}
19 PATH = ${cfg.database.path}
22 ROOT = ${cfg.repositoryRoot}
25 DOMAIN = ${cfg.domain}
26 HTTP_ADDR = ${cfg.httpAddress}
27 HTTP_PORT = ${toString cfg.httpPort}
28 ROOT_URL = ${cfg.rootUrl}
32 COOKIE_SECURE = ${boolToString cfg.cookieSecure}
35 SECRET_KEY = #secretkey#
39 ROOT_PATH = ${cfg.stateDir}/log
51 description = lib.mdDoc "Enable Go Git Service.";
54 useWizard = mkOption {
57 description = lib.mdDoc "Do not generate a configuration and use Gogs' installation wizard instead. The first registered user will be administrator.";
61 default = "/var/lib/gogs";
63 description = lib.mdDoc "Gogs data directory.";
69 description = lib.mdDoc "User account under which Gogs runs.";
75 description = lib.mdDoc "Group account under which Gogs runs.";
80 type = types.enum [ "sqlite3" "mysql" "postgres" ];
83 description = lib.mdDoc "Database engine to use.";
88 default = "127.0.0.1";
89 description = lib.mdDoc "Database host address.";
95 description = lib.mdDoc "Database host port.";
101 description = lib.mdDoc "Database name.";
107 description = lib.mdDoc "Database user.";
110 password = mkOption {
113 description = lib.mdDoc ''
114 The password corresponding to {option}`database.user`.
115 Warning: this is stored in cleartext in the Nix store!
116 Use {option}`database.passwordFile` instead.
120 passwordFile = mkOption {
121 type = types.nullOr types.path;
123 example = "/run/keys/gogs-dbpassword";
124 description = lib.mdDoc ''
125 A file containing the password corresponding to
126 {option}`database.user`.
132 default = "${cfg.stateDir}/data/gogs.db";
133 defaultText = literalExpression ''"''${config.${opt.stateDir}}/data/gogs.db"'';
134 description = lib.mdDoc "Path to the sqlite3 database file.";
140 default = "Gogs: Go Git Service";
141 description = lib.mdDoc "Application name.";
144 repositoryRoot = mkOption {
146 default = "${cfg.stateDir}/repositories";
147 defaultText = literalExpression ''"''${config.${opt.stateDir}}/repositories"'';
148 description = lib.mdDoc "Path to the git repositories.";
153 default = "localhost";
154 description = lib.mdDoc "Domain name of your server.";
159 default = "http://localhost:3000/";
160 description = lib.mdDoc "Full public URL of Gogs server.";
163 httpAddress = mkOption {
166 description = lib.mdDoc "HTTP listen address.";
169 httpPort = mkOption {
172 description = lib.mdDoc "HTTP listen port.";
175 cookieSecure = mkOption {
178 description = lib.mdDoc ''
179 Marks session cookies as "secure" as a hint for browsers to only send
180 them via HTTPS. This option is recommend, if Gogs is being served over HTTPS.
184 extraConfig = mkOption {
187 description = lib.mdDoc "Configuration lines appended to the generated Gogs configuration file.";
192 config = mkIf cfg.enable {
194 systemd.services.gogs = {
195 description = "Gogs (Go Git Service)";
196 after = [ "network.target" ];
197 wantedBy = [ "multi-user.target" ];
198 path = [ pkgs.gogs ];
201 runConfig = "${cfg.stateDir}/custom/conf/app.ini";
202 secretKey = "${cfg.stateDir}/custom/conf/secret_key";
204 mkdir -p ${cfg.stateDir}
206 # copy custom configuration and generate a random secret key if needed
207 ${optionalString (cfg.useWizard == false) ''
208 mkdir -p ${cfg.stateDir}/custom/conf
209 cp -f ${configFile} ${runConfig}
211 if [ ! -e ${secretKey} ]; then
212 head -c 16 /dev/urandom | base64 > ${secretKey}
215 KEY=$(head -n1 ${secretKey})
216 DBPASS=$(head -n1 ${cfg.database.passwordFile})
217 sed -e "s,#secretkey#,$KEY,g" \
218 -e "s,#dbpass#,$DBPASS,g" \
220 chmod 440 ${runConfig} ${secretKey}
223 mkdir -p ${cfg.repositoryRoot}
224 # update all hooks' binary paths
225 HOOKS=$(find ${cfg.repositoryRoot} -mindepth 4 -maxdepth 4 -type f -wholename "*git/hooks/*")
228 sed -ri 's,/nix/store/[a-z0-9.-]+/bin/gogs,${pkgs.gogs}/bin/gogs,g' $HOOKS
229 sed -ri 's,/nix/store/[a-z0-9.-]+/bin/env,${pkgs.coreutils}/bin/env,g' $HOOKS
230 sed -ri 's,/nix/store/[a-z0-9.-]+/bin/bash,${pkgs.bash}/bin/bash,g' $HOOKS
231 sed -ri 's,/nix/store/[a-z0-9.-]+/bin/perl,${pkgs.perl}/bin/perl,g' $HOOKS
239 WorkingDirectory = cfg.stateDir;
240 ExecStart = "${pkgs.gogs}/bin/gogs web";
247 GOGS_WORK_DIR = cfg.stateDir;
251 users = mkIf (cfg.user == "gogs") {
253 description = "Go Git Service";
254 uid = config.ids.uids.gogs;
260 groups.gogs.gid = config.ids.gids.gogs;
263 warnings = optional (cfg.database.password != "")
264 ''config.services.gogs.database.password will be stored as plaintext
265 in the Nix store. Use database.passwordFile instead.'';
267 # Create database passwordFile default when password is configured.
268 services.gogs.database.passwordFile =
269 (mkDefault (toString (pkgs.writeTextFile {
270 name = "gogs-database-password";
271 text = cfg.database.password;