mastodon = ./webapps/mastodon.nix;
mediagoblin = ./webapps/mediagoblin.nix;
peertube = ./webapps/peertube.nix;
-}
+} // (if builtins.pathExists ./private then import ./private else {})
--- /dev/null
+{
+ # adatped from nixpkgs/nixos/modules/services/web-servers/apache-httpd/default.nix
+ httpdProd = import ./httpd-service-builder.nix { httpdName = "Prod"; withUsers = false; };
+ httpdInte = import ./httpd-service-builder.nix { httpdName = "Inte"; withUsers = false; };
+ httpdTools = import ./httpd-service-builder.nix { httpdName = "Tools"; withUsers = true; };
+}
+# to help backporting this builder should stay as close as possible to
+# nixos/modules/services/web-servers/apache-httpd/default.nix
+{ httpdName, withUsers ? true }:
{ config, lib, pkgs, ... }:
with lib;
let
- mainCfg = config.services.httpdTools;
+ mainCfg = config.services."httpd${httpdName}";
httpd = mainCfg.package.out;
options = {
- services.httpdTools = {
+ services."httpd${httpdName}" = {
enable = mkOption {
type = types.bool;
}
# Include the options shared between the main server and virtual hosts.
- // (import ./per-server-options.nix {
+ // (import <nixpkgs/nixos/modules/services/web-servers/apache-httpd/per-server-options.nix> {
inherit lib;
forMainServer = true;
});
###### implementation
- config = mkIf config.services.httpdTools.enable {
+ config = mkIf config.services."httpd${httpdName}".enable {
assertions = [ { assertion = mainCfg.enableSSL == true
-> mainCfg.sslServerCert != null
warnings = map (cfg: ''apache-httpd's port option is deprecated. Use listen = [{/*ip = "*"; */ port = ${toString cfg.port};}]; instead'' ) (lib.filter (cfg: cfg.port != 0) allHosts);
- users.users = optionalAttrs (mainCfg.user == "wwwrun") (singleton
+ users.users = optionalAttrs (withUsers && mainCfg.user == "wwwrun") (singleton
{ name = "wwwrun";
group = mainCfg.group;
description = "Apache httpd user";
uid = config.ids.uids.wwwrun;
});
- users.groups = optionalAttrs (mainCfg.group == "wwwrun") (singleton
+ users.groups = optionalAttrs (withUsers && mainCfg.group == "wwwrun") (singleton
{ name = "wwwrun";
gid = config.ids.gids.wwwrun;
});
environment.systemPackages = [httpd] ++ concatMap (svc: svc.extraPath) allSubservices;
- services.httpdTools.phpOptions =
+ services."httpd${httpdName}".phpOptions =
''
; Needed for PHP's mail() function.
sendmail_path = sendmail -t -i
date.timezone = "${config.time.timeZone}"
'';
- systemd.services.httpdTools =
+ systemd.services."httpd${httpdName}" =
{ description = "Apache HTTPD";
wantedBy = [ "multi-user.target" ];
+++ /dev/null
-{ config, lib, pkgs, ... }:
-
-with lib;
-
-let
-
- mainCfg = config.services.httpdInte;
-
- httpd = mainCfg.package.out;
-
- version24 = !versionOlder httpd.version "2.4";
-
- httpdConf = mainCfg.configFile;
-
- php = mainCfg.phpPackage.override { apacheHttpd = httpd.dev; /* otherwise it only gets .out */ };
-
- phpMajorVersion = head (splitString "." php.version);
-
- mod_perl = pkgs.apacheHttpdPackages.mod_perl.override { apacheHttpd = httpd; };
-
- defaultListen = cfg: if cfg.enableSSL
- then [{ip = "*"; port = 443;}]
- else [{ip = "*"; port = 80;}];
-
- getListen = cfg:
- let list = (lib.optional (cfg.port != 0) {ip = "*"; port = cfg.port;}) ++ cfg.listen;
- in if list == []
- then defaultListen cfg
- else list;
-
- listenToString = l: "${l.ip}:${toString l.port}";
-
- extraModules = attrByPath ["extraModules"] [] mainCfg;
- extraForeignModules = filter isAttrs extraModules;
- extraApacheModules = filter isString extraModules;
-
-
- makeServerInfo = cfg: {
- # Canonical name must not include a trailing slash.
- canonicalNames =
- let defaultPort = (head (defaultListen cfg)).port; in
- map (port:
- (if cfg.enableSSL then "https" else "http") + "://" +
- cfg.hostName +
- (if port != defaultPort then ":${toString port}" else "")
- ) (map (x: x.port) (getListen cfg));
-
- # Admin address: inherit from the main server if not specified for
- # a virtual host.
- adminAddr = if cfg.adminAddr != null then cfg.adminAddr else mainCfg.adminAddr;
-
- vhostConfig = cfg;
- serverConfig = mainCfg;
- fullConfig = config; # machine config
- };
-
-
- allHosts = [mainCfg] ++ mainCfg.virtualHosts;
-
-
- callSubservices = serverInfo: defs:
- let f = svc:
- let
- svcFunction =
- if svc ? function then svc.function
- # instead of using serviceType="mediawiki"; you can copy mediawiki.nix to any location outside nixpkgs, modify it at will, and use serviceExpression=./mediawiki.nix;
- else if svc ? serviceExpression then import (toString svc.serviceExpression)
- else import (toString "${toString ./.}/${if svc ? serviceType then svc.serviceType else svc.serviceName}.nix");
- config = (evalModules
- { modules = [ { options = res.options; config = svc.config or svc; } ];
- check = false;
- }).config;
- defaults = {
- extraConfig = "";
- extraModules = [];
- extraModulesPre = [];
- extraPath = [];
- extraServerPath = [];
- globalEnvVars = [];
- robotsEntries = "";
- startupScript = "";
- enablePHP = false;
- enablePerl = false;
- phpOptions = "";
- options = {};
- documentRoot = null;
- };
- res = defaults // svcFunction { inherit config lib pkgs serverInfo php; };
- in res;
- in map f defs;
-
-
- # !!! callSubservices is expensive
- subservicesFor = cfg: callSubservices (makeServerInfo cfg) cfg.extraSubservices;
-
- mainSubservices = subservicesFor mainCfg;
-
- allSubservices = mainSubservices ++ concatMap subservicesFor mainCfg.virtualHosts;
-
-
- enableSSL = any (vhost: vhost.enableSSL) allHosts;
-
-
- # Names of modules from ${httpd}/modules that we want to load.
- apacheModules =
- [ # HTTP authentication mechanisms: basic and digest.
- "auth_basic" "auth_digest"
-
- # Authentication: is the user who he claims to be?
- "authn_file" "authn_dbm" "authn_anon"
- (if version24 then "authn_core" else "authn_alias")
-
- # Authorization: is the user allowed access?
- "authz_user" "authz_groupfile" "authz_host"
-
- # Other modules.
- "ext_filter" "include" "log_config" "env" "mime_magic"
- "cern_meta" "expires" "headers" "usertrack" /* "unique_id" */ "setenvif"
- "mime" "dav" "status" "autoindex" "asis" "info" "dav_fs"
- "vhost_alias" "negotiation" "dir" "imagemap" "actions" "speling"
- "userdir" "alias" "rewrite" "proxy" "proxy_http"
- ]
- ++ optionals version24 [
- "mpm_${mainCfg.multiProcessingModule}"
- "authz_core"
- "unixd"
- "cache" "cache_disk"
- "slotmem_shm"
- "socache_shmcb"
- # For compatibility with old configurations, the new module mod_access_compat is provided.
- "access_compat"
- ]
- ++ (if mainCfg.multiProcessingModule == "prefork" then [ "cgi" ] else [ "cgid" ])
- ++ optional enableSSL "ssl"
- ++ extraApacheModules;
-
-
- allDenied = if version24 then ''
- Require all denied
- '' else ''
- Order deny,allow
- Deny from all
- '';
-
- allGranted = if version24 then ''
- Require all granted
- '' else ''
- Order allow,deny
- Allow from all
- '';
-
-
- loggingConf = (if mainCfg.logFormat != "none" then ''
- ErrorLog ${mainCfg.logDir}/error.log
-
- LogLevel notice
-
- LogFormat "%h %l %u %t \"%r\" %>s %b \"%{Referer}i\" \"%{User-Agent}i\"" combined
- LogFormat "%h %l %u %t \"%r\" %>s %b" common
- LogFormat "%{Referer}i -> %U" referer
- LogFormat "%{User-agent}i" agent
-
- CustomLog ${mainCfg.logDir}/access.log ${mainCfg.logFormat}
- '' else ''
- ErrorLog /dev/null
- '');
-
-
- browserHacks = ''
- BrowserMatch "Mozilla/2" nokeepalive
- BrowserMatch "MSIE 4\.0b2;" nokeepalive downgrade-1.0 force-response-1.0
- BrowserMatch "RealPlayer 4\.0" force-response-1.0
- BrowserMatch "Java/1\.0" force-response-1.0
- BrowserMatch "JDK/1\.0" force-response-1.0
- BrowserMatch "Microsoft Data Access Internet Publishing Provider" redirect-carefully
- BrowserMatch "^WebDrive" redirect-carefully
- BrowserMatch "^WebDAVFS/1.[012]" redirect-carefully
- BrowserMatch "^gnome-vfs" redirect-carefully
- '';
-
-
- sslConf = ''
- SSLSessionCache ${if version24 then "shmcb" else "shm"}:${mainCfg.stateDir}/ssl_scache(512000)
-
- ${if version24 then "Mutex" else "SSLMutex"} posixsem
-
- SSLRandomSeed startup builtin
- SSLRandomSeed connect builtin
-
- SSLProtocol ${mainCfg.sslProtocols}
- SSLCipherSuite ${mainCfg.sslCiphers}
- SSLHonorCipherOrder on
- '';
-
-
- mimeConf = ''
- TypesConfig ${httpd}/conf/mime.types
-
- AddType application/x-x509-ca-cert .crt
- AddType application/x-pkcs7-crl .crl
- AddType application/x-httpd-php .php .phtml
-
- <IfModule mod_mime_magic.c>
- MIMEMagicFile ${httpd}/conf/magic
- </IfModule>
- '';
-
-
- perServerConf = isMainServer: cfg: let
-
- serverInfo = makeServerInfo cfg;
-
- subservices = callSubservices serverInfo cfg.extraSubservices;
-
- maybeDocumentRoot = fold (svc: acc:
- if acc == null then svc.documentRoot else assert svc.documentRoot == null; acc
- ) null ([ cfg ] ++ subservices);
-
- documentRoot = if maybeDocumentRoot != null then maybeDocumentRoot else
- pkgs.runCommand "empty" { preferLocalBuild = true; } "mkdir -p $out";
-
- documentRootConf = ''
- DocumentRoot "${documentRoot}"
-
- <Directory "${documentRoot}">
- Options Indexes FollowSymLinks
- AllowOverride None
- ${allGranted}
- </Directory>
- '';
-
- robotsTxt =
- concatStringsSep "\n" (filter (x: x != "") (
- # If this is a vhost, the include the entries for the main server as well.
- (if isMainServer then [] else [mainCfg.robotsEntries] ++ map (svc: svc.robotsEntries) mainSubservices)
- ++ [cfg.robotsEntries]
- ++ (map (svc: svc.robotsEntries) subservices)));
-
- in ''
- ${concatStringsSep "\n" (map (n: "ServerName ${n}") serverInfo.canonicalNames)}
-
- ${concatMapStrings (alias: "ServerAlias ${alias}\n") cfg.serverAliases}
-
- ${if cfg.sslServerCert != null then ''
- SSLCertificateFile ${cfg.sslServerCert}
- SSLCertificateKeyFile ${cfg.sslServerKey}
- ${if cfg.sslServerChain != null then ''
- SSLCertificateChainFile ${cfg.sslServerChain}
- '' else ""}
- '' else ""}
-
- ${if cfg.enableSSL then ''
- SSLEngine on
- '' else if enableSSL then /* i.e., SSL is enabled for some host, but not this one */
- ''
- SSLEngine off
- '' else ""}
-
- ${if isMainServer || cfg.adminAddr != null then ''
- ServerAdmin ${cfg.adminAddr}
- '' else ""}
-
- ${if !isMainServer && mainCfg.logPerVirtualHost then ''
- ErrorLog ${mainCfg.logDir}/error-${cfg.hostName}.log
- CustomLog ${mainCfg.logDir}/access-${cfg.hostName}.log ${cfg.logFormat}
- '' else ""}
-
- ${optionalString (robotsTxt != "") ''
- Alias /robots.txt ${pkgs.writeText "robots.txt" robotsTxt}
- ''}
-
- ${if isMainServer || maybeDocumentRoot != null then documentRootConf else ""}
-
- ${if cfg.enableUserDir then ''
-
- UserDir public_html
- UserDir disabled root
-
- <Directory "/home/*/public_html">
- AllowOverride FileInfo AuthConfig Limit Indexes
- Options MultiViews Indexes SymLinksIfOwnerMatch IncludesNoExec
- <Limit GET POST OPTIONS>
- ${allGranted}
- </Limit>
- <LimitExcept GET POST OPTIONS>
- ${allDenied}
- </LimitExcept>
- </Directory>
-
- '' else ""}
-
- ${if cfg.globalRedirect != null && cfg.globalRedirect != "" then ''
- RedirectPermanent / ${cfg.globalRedirect}
- '' else ""}
-
- ${
- let makeFileConf = elem: ''
- Alias ${elem.urlPath} ${elem.file}
- '';
- in concatMapStrings makeFileConf cfg.servedFiles
- }
-
- ${
- let makeDirConf = elem: ''
- Alias ${elem.urlPath} ${elem.dir}/
- <Directory ${elem.dir}>
- Options +Indexes
- ${allGranted}
- AllowOverride All
- </Directory>
- '';
- in concatMapStrings makeDirConf cfg.servedDirs
- }
-
- ${concatMapStrings (svc: svc.extraConfig) subservices}
-
- ${cfg.extraConfig}
- '';
-
-
- confFile = pkgs.writeText "httpd.conf" ''
-
- ServerRoot ${httpd}
-
- ${optionalString version24 ''
- DefaultRuntimeDir ${mainCfg.stateDir}/runtime
- ''}
-
- PidFile ${mainCfg.stateDir}/httpd.pid
-
- ${optionalString (mainCfg.multiProcessingModule != "prefork") ''
- # mod_cgid requires this.
- ScriptSock ${mainCfg.stateDir}/cgisock
- ''}
-
- <IfModule prefork.c>
- MaxClients ${toString mainCfg.maxClients}
- MaxRequestsPerChild ${toString mainCfg.maxRequestsPerChild}
- </IfModule>
-
- ${let
- listen = concatMap getListen allHosts;
- toStr = listen: "Listen ${listenToString listen}\n";
- uniqueListen = uniqList {inputList = map toStr listen;};
- in concatStrings uniqueListen
- }
-
- User ${mainCfg.user}
- Group ${mainCfg.group}
-
- ${let
- load = {name, path}: "LoadModule ${name}_module ${path}\n";
- allModules =
- concatMap (svc: svc.extraModulesPre) allSubservices
- ++ map (name: {inherit name; path = "${httpd}/modules/mod_${name}.so";}) apacheModules
- ++ optional mainCfg.enableMellon { name = "auth_mellon"; path = "${pkgs.apacheHttpdPackages.mod_auth_mellon}/modules/mod_auth_mellon.so"; }
- ++ optional enablePHP { name = "php${phpMajorVersion}"; path = "${php}/modules/libphp${phpMajorVersion}.so"; }
- ++ optional enablePerl { name = "perl"; path = "${mod_perl}/modules/mod_perl.so"; }
- ++ concatMap (svc: svc.extraModules) allSubservices
- ++ extraForeignModules;
- in concatMapStrings load allModules
- }
-
- AddHandler type-map var
-
- <Files ~ "^\.ht">
- ${allDenied}
- </Files>
-
- ${mimeConf}
- ${loggingConf}
- ${browserHacks}
-
- Include ${httpd}/conf/extra/httpd-default.conf
- Include ${httpd}/conf/extra/httpd-autoindex.conf
- Include ${httpd}/conf/extra/httpd-multilang-errordoc.conf
- Include ${httpd}/conf/extra/httpd-languages.conf
-
- TraceEnable off
-
- ${if enableSSL then sslConf else ""}
-
- # Fascist default - deny access to everything.
- <Directory />
- Options FollowSymLinks
- AllowOverride None
- ${allDenied}
- </Directory>
-
- # Generate directives for the main server.
- ${perServerConf true mainCfg}
-
- # Always enable virtual hosts; it doesn't seem to hurt.
- ${let
- listen = concatMap getListen allHosts;
- uniqueListen = uniqList {inputList = listen;};
- directives = concatMapStrings (listen: "NameVirtualHost ${listenToString listen}\n") uniqueListen;
- in optionalString (!version24) directives
- }
-
- ${let
- makeVirtualHost = vhost: ''
- <VirtualHost ${concatStringsSep " " (map listenToString (getListen vhost))}>
- ${perServerConf false vhost}
- </VirtualHost>
- '';
- in concatMapStrings makeVirtualHost mainCfg.virtualHosts
- }
- '';
-
-
- enablePHP = mainCfg.enablePHP || any (svc: svc.enablePHP) allSubservices;
-
- enablePerl = mainCfg.enablePerl || any (svc: svc.enablePerl) allSubservices;
-
-
- # Generate the PHP configuration file. Should probably be factored
- # out into a separate module.
- phpIni = pkgs.runCommand "php.ini"
- { options = concatStringsSep "\n"
- ([ mainCfg.phpOptions ] ++ (map (svc: svc.phpOptions) allSubservices));
- preferLocalBuild = true;
- }
- ''
- cat ${php}/etc/php.ini > $out
- echo "$options" >> $out
- '';
-
-in
-
-
-{
-
- ###### interface
-
- options = {
-
- services.httpdInte = {
-
- enable = mkOption {
- type = types.bool;
- default = false;
- description = "Whether to enable the Apache HTTP Server.";
- };
-
- package = mkOption {
- type = types.package;
- default = pkgs.apacheHttpd;
- defaultText = "pkgs.apacheHttpd";
- description = ''
- Overridable attribute of the Apache HTTP Server package to use.
- '';
- };
-
- configFile = mkOption {
- type = types.path;
- default = confFile;
- defaultText = "confFile";
- example = literalExample ''pkgs.writeText "httpd.conf" "# my custom config file ..."'';
- description = ''
- Override the configuration file used by Apache. By default,
- NixOS generates one automatically.
- '';
- };
-
- extraConfig = mkOption {
- type = types.lines;
- default = "";
- description = ''
- Cnfiguration lines appended to the generated Apache
- configuration file. Note that this mechanism may not work
- when <option>configFile</option> is overridden.
- '';
- };
-
- extraModules = mkOption {
- type = types.listOf types.unspecified;
- default = [];
- example = literalExample ''[ "proxy_connect" { name = "php5"; path = "''${pkgs.php}/modules/libphp5.so"; } ]'';
- description = ''
- Additional Apache modules to be used. These can be
- specified as a string in the case of modules distributed
- with Apache, or as an attribute set specifying the
- <varname>name</varname> and <varname>path</varname> of the
- module.
- '';
- };
-
- logPerVirtualHost = mkOption {
- type = types.bool;
- default = false;
- description = ''
- If enabled, each virtual host gets its own
- <filename>access.log</filename> and
- <filename>error.log</filename>, namely suffixed by the
- <option>hostName</option> of the virtual host.
- '';
- };
-
- user = mkOption {
- type = types.str;
- default = "wwwrun";
- description = ''
- User account under which httpd runs. The account is created
- automatically if it doesn't exist.
- '';
- };
-
- group = mkOption {
- type = types.str;
- default = "wwwrun";
- description = ''
- Group under which httpd runs. The account is created
- automatically if it doesn't exist.
- '';
- };
-
- logDir = mkOption {
- type = types.path;
- default = "/var/log/httpd";
- description = ''
- Directory for Apache's log files. It is created automatically.
- '';
- };
-
- stateDir = mkOption {
- type = types.path;
- default = "/run/httpd";
- description = ''
- Directory for Apache's transient runtime state (such as PID
- files). It is created automatically. Note that the default,
- <filename>/run/httpd</filename>, is deleted at boot time.
- '';
- };
-
- virtualHosts = mkOption {
- type = types.listOf (types.submodule (
- { options = import <nixpkgs/nixos/modules/services/web-servers/apache-httpd/per-server-options.nix> {
- inherit lib;
- forMainServer = false;
- };
- }));
- default = [];
- example = [
- { hostName = "foo";
- documentRoot = "/data/webroot-foo";
- }
- { hostName = "bar";
- documentRoot = "/data/webroot-bar";
- }
- ];
- description = ''
- Specification of the virtual hosts served by Apache. Each
- element should be an attribute set specifying the
- configuration of the virtual host. The available options
- are the non-global options permissible for the main host.
- '';
- };
-
- enableMellon = mkOption {
- type = types.bool;
- default = false;
- description = "Whether to enable the mod_auth_mellon module.";
- };
-
- enablePHP = mkOption {
- type = types.bool;
- default = false;
- description = "Whether to enable the PHP module.";
- };
-
- phpPackage = mkOption {
- type = types.package;
- default = pkgs.php;
- defaultText = "pkgs.php";
- description = ''
- Overridable attribute of the PHP package to use.
- '';
- };
-
- enablePerl = mkOption {
- type = types.bool;
- default = false;
- description = "Whether to enable the Perl module (mod_perl).";
- };
-
- phpOptions = mkOption {
- type = types.lines;
- default = "";
- example =
- ''
- date.timezone = "CET"
- '';
- description =
- "Options appended to the PHP configuration file <filename>php.ini</filename>.";
- };
-
- multiProcessingModule = mkOption {
- type = types.str;
- default = "prefork";
- example = "worker";
- description =
- ''
- Multi-processing module to be used by Apache. Available
- modules are <literal>prefork</literal> (the default;
- handles each request in a separate child process),
- <literal>worker</literal> (hybrid approach that starts a
- number of child processes each running a number of
- threads) and <literal>event</literal> (a recent variant of
- <literal>worker</literal> that handles persistent
- connections more efficiently).
- '';
- };
-
- maxClients = mkOption {
- type = types.int;
- default = 150;
- example = 8;
- description = "Maximum number of httpd processes (prefork)";
- };
-
- maxRequestsPerChild = mkOption {
- type = types.int;
- default = 0;
- example = 500;
- description =
- "Maximum number of httpd requests answered per httpd child (prefork), 0 means unlimited";
- };
-
- sslCiphers = mkOption {
- type = types.str;
- default = "HIGH:!aNULL:!MD5:!EXP";
- description = "Cipher Suite available for negotiation in SSL proxy handshake.";
- };
-
- sslProtocols = mkOption {
- type = types.str;
- default = "All -SSLv2 -SSLv3 -TLSv1";
- example = "All -SSLv2 -SSLv3";
- description = "Allowed SSL/TLS protocol versions.";
- };
- }
-
- # Include the options shared between the main server and virtual hosts.
- // (import ./per-server-options.nix {
- inherit lib;
- forMainServer = true;
- });
-
- };
-
-
- ###### implementation
-
- config = mkIf config.services.httpdInte.enable {
-
- assertions = [ { assertion = mainCfg.enableSSL == true
- -> mainCfg.sslServerCert != null
- && mainCfg.sslServerKey != null;
- message = "SSL is enabled for httpd, but sslServerCert and/or sslServerKey haven't been specified."; }
- ];
-
- warnings = map (cfg: ''apache-httpd's port option is deprecated. Use listen = [{/*ip = "*"; */ port = ${toString cfg.port};}]; instead'' ) (lib.filter (cfg: cfg.port != 0) allHosts);
-
- environment.systemPackages = [httpd] ++ concatMap (svc: svc.extraPath) allSubservices;
-
- services.httpdInte.phpOptions =
- ''
- ; Needed for PHP's mail() function.
- sendmail_path = sendmail -t -i
-
- ; Don't advertise PHP
- expose_php = off
- '' + optionalString (!isNull config.time.timeZone) ''
-
- ; Apparently PHP doesn't use $TZ.
- date.timezone = "${config.time.timeZone}"
- '';
-
- systemd.services.httpdInte =
- { description = "Apache HTTPD";
-
- wantedBy = [ "multi-user.target" ];
- wants = [ "keys.target" ];
- after = [ "network.target" "fs.target" "postgresql.service" "keys.target" ];
-
- path =
- [ httpd pkgs.coreutils pkgs.gnugrep ]
- ++ optional enablePHP pkgs.system-sendmail # Needed for PHP's mail() function.
- ++ concatMap (svc: svc.extraServerPath) allSubservices;
-
- environment =
- optionalAttrs enablePHP { PHPRC = phpIni; }
- // optionalAttrs mainCfg.enableMellon { LD_LIBRARY_PATH = "${pkgs.xmlsec}/lib"; }
- // (listToAttrs (concatMap (svc: svc.globalEnvVars) allSubservices));
-
- preStart =
- ''
- mkdir -m 0750 -p ${mainCfg.stateDir}
- [ $(id -u) != 0 ] || chown root.${mainCfg.group} ${mainCfg.stateDir}
- ${optionalString version24 ''
- mkdir -m 0750 -p "${mainCfg.stateDir}/runtime"
- [ $(id -u) != 0 ] || chown root.${mainCfg.group} "${mainCfg.stateDir}/runtime"
- ''}
- mkdir -m 0700 -p ${mainCfg.logDir}
-
- # Get rid of old semaphores. These tend to accumulate across
- # server restarts, eventually preventing it from restarting
- # successfully.
- for i in $(${pkgs.utillinux}/bin/ipcs -s | grep ' ${mainCfg.user} ' | cut -f2 -d ' '); do
- ${pkgs.utillinux}/bin/ipcrm -s $i
- done
-
- # Run the startup hooks for the subservices.
- for i in ${toString (map (svn: svn.startupScript) allSubservices)}; do
- echo Running Apache startup hook $i...
- $i
- done
- '';
-
- serviceConfig.ExecStart = "@${httpd}/bin/httpd httpd -f ${httpdConf}";
- serviceConfig.ExecStop = "${httpd}/bin/httpd -f ${httpdConf} -k graceful-stop";
- serviceConfig.ExecReload = "${httpd}/bin/httpd -f ${httpdConf} -k graceful";
- serviceConfig.Type = "forking";
- serviceConfig.PIDFile = "${mainCfg.stateDir}/httpd.pid";
- serviceConfig.Restart = "always";
- serviceConfig.RestartSec = "5s";
- };
-
- };
-}
+++ /dev/null
-{ config, lib, pkgs, ... }:
-
-with lib;
-
-let
-
- mainCfg = config.services.httpdProd;
-
- httpd = mainCfg.package.out;
-
- version24 = !versionOlder httpd.version "2.4";
-
- httpdConf = mainCfg.configFile;
-
- php = mainCfg.phpPackage.override { apacheHttpd = httpd.dev; /* otherwise it only gets .out */ };
-
- phpMajorVersion = head (splitString "." php.version);
-
- mod_perl = pkgs.apacheHttpdPackages.mod_perl.override { apacheHttpd = httpd; };
-
- defaultListen = cfg: if cfg.enableSSL
- then [{ip = "*"; port = 443;}]
- else [{ip = "*"; port = 80;}];
-
- getListen = cfg:
- let list = (lib.optional (cfg.port != 0) {ip = "*"; port = cfg.port;}) ++ cfg.listen;
- in if list == []
- then defaultListen cfg
- else list;
-
- listenToString = l: "${l.ip}:${toString l.port}";
-
- extraModules = attrByPath ["extraModules"] [] mainCfg;
- extraForeignModules = filter isAttrs extraModules;
- extraApacheModules = filter isString extraModules;
-
-
- makeServerInfo = cfg: {
- # Canonical name must not include a trailing slash.
- canonicalNames =
- let defaultPort = (head (defaultListen cfg)).port; in
- map (port:
- (if cfg.enableSSL then "https" else "http") + "://" +
- cfg.hostName +
- (if port != defaultPort then ":${toString port}" else "")
- ) (map (x: x.port) (getListen cfg));
-
- # Admin address: inherit from the main server if not specified for
- # a virtual host.
- adminAddr = if cfg.adminAddr != null then cfg.adminAddr else mainCfg.adminAddr;
-
- vhostConfig = cfg;
- serverConfig = mainCfg;
- fullConfig = config; # machine config
- };
-
-
- allHosts = [mainCfg] ++ mainCfg.virtualHosts;
-
-
- callSubservices = serverInfo: defs:
- let f = svc:
- let
- svcFunction =
- if svc ? function then svc.function
- # instead of using serviceType="mediawiki"; you can copy mediawiki.nix to any location outside nixpkgs, modify it at will, and use serviceExpression=./mediawiki.nix;
- else if svc ? serviceExpression then import (toString svc.serviceExpression)
- else import (toString "${toString ./.}/${if svc ? serviceType then svc.serviceType else svc.serviceName}.nix");
- config = (evalModules
- { modules = [ { options = res.options; config = svc.config or svc; } ];
- check = false;
- }).config;
- defaults = {
- extraConfig = "";
- extraModules = [];
- extraModulesPre = [];
- extraPath = [];
- extraServerPath = [];
- globalEnvVars = [];
- robotsEntries = "";
- startupScript = "";
- enablePHP = false;
- enablePerl = false;
- phpOptions = "";
- options = {};
- documentRoot = null;
- };
- res = defaults // svcFunction { inherit config lib pkgs serverInfo php; };
- in res;
- in map f defs;
-
-
- # !!! callSubservices is expensive
- subservicesFor = cfg: callSubservices (makeServerInfo cfg) cfg.extraSubservices;
-
- mainSubservices = subservicesFor mainCfg;
-
- allSubservices = mainSubservices ++ concatMap subservicesFor mainCfg.virtualHosts;
-
-
- enableSSL = any (vhost: vhost.enableSSL) allHosts;
-
-
- # Names of modules from ${httpd}/modules that we want to load.
- apacheModules =
- [ # HTTP authentication mechanisms: basic and digest.
- "auth_basic" "auth_digest"
-
- # Authentication: is the user who he claims to be?
- "authn_file" "authn_dbm" "authn_anon"
- (if version24 then "authn_core" else "authn_alias")
-
- # Authorization: is the user allowed access?
- "authz_user" "authz_groupfile" "authz_host"
-
- # Other modules.
- "ext_filter" "include" "log_config" "env" "mime_magic"
- "cern_meta" "expires" "headers" "usertrack" /* "unique_id" */ "setenvif"
- "mime" "dav" "status" "autoindex" "asis" "info" "dav_fs"
- "vhost_alias" "negotiation" "dir" "imagemap" "actions" "speling"
- "userdir" "alias" "rewrite" "proxy" "proxy_http"
- ]
- ++ optionals version24 [
- "mpm_${mainCfg.multiProcessingModule}"
- "authz_core"
- "unixd"
- "cache" "cache_disk"
- "slotmem_shm"
- "socache_shmcb"
- # For compatibility with old configurations, the new module mod_access_compat is provided.
- "access_compat"
- ]
- ++ (if mainCfg.multiProcessingModule == "prefork" then [ "cgi" ] else [ "cgid" ])
- ++ optional enableSSL "ssl"
- ++ extraApacheModules;
-
-
- allDenied = if version24 then ''
- Require all denied
- '' else ''
- Order deny,allow
- Deny from all
- '';
-
- allGranted = if version24 then ''
- Require all granted
- '' else ''
- Order allow,deny
- Allow from all
- '';
-
-
- loggingConf = (if mainCfg.logFormat != "none" then ''
- ErrorLog ${mainCfg.logDir}/error.log
-
- LogLevel notice
-
- LogFormat "%h %l %u %t \"%r\" %>s %b \"%{Referer}i\" \"%{User-Agent}i\"" combined
- LogFormat "%h %l %u %t \"%r\" %>s %b" common
- LogFormat "%{Referer}i -> %U" referer
- LogFormat "%{User-agent}i" agent
-
- CustomLog ${mainCfg.logDir}/access.log ${mainCfg.logFormat}
- '' else ''
- ErrorLog /dev/null
- '');
-
-
- browserHacks = ''
- BrowserMatch "Mozilla/2" nokeepalive
- BrowserMatch "MSIE 4\.0b2;" nokeepalive downgrade-1.0 force-response-1.0
- BrowserMatch "RealPlayer 4\.0" force-response-1.0
- BrowserMatch "Java/1\.0" force-response-1.0
- BrowserMatch "JDK/1\.0" force-response-1.0
- BrowserMatch "Microsoft Data Access Internet Publishing Provider" redirect-carefully
- BrowserMatch "^WebDrive" redirect-carefully
- BrowserMatch "^WebDAVFS/1.[012]" redirect-carefully
- BrowserMatch "^gnome-vfs" redirect-carefully
- '';
-
-
- sslConf = ''
- SSLSessionCache ${if version24 then "shmcb" else "shm"}:${mainCfg.stateDir}/ssl_scache(512000)
-
- ${if version24 then "Mutex" else "SSLMutex"} posixsem
-
- SSLRandomSeed startup builtin
- SSLRandomSeed connect builtin
-
- SSLProtocol ${mainCfg.sslProtocols}
- SSLCipherSuite ${mainCfg.sslCiphers}
- SSLHonorCipherOrder on
- '';
-
-
- mimeConf = ''
- TypesConfig ${httpd}/conf/mime.types
-
- AddType application/x-x509-ca-cert .crt
- AddType application/x-pkcs7-crl .crl
- AddType application/x-httpd-php .php .phtml
-
- <IfModule mod_mime_magic.c>
- MIMEMagicFile ${httpd}/conf/magic
- </IfModule>
- '';
-
-
- perServerConf = isMainServer: cfg: let
-
- serverInfo = makeServerInfo cfg;
-
- subservices = callSubservices serverInfo cfg.extraSubservices;
-
- maybeDocumentRoot = fold (svc: acc:
- if acc == null then svc.documentRoot else assert svc.documentRoot == null; acc
- ) null ([ cfg ] ++ subservices);
-
- documentRoot = if maybeDocumentRoot != null then maybeDocumentRoot else
- pkgs.runCommand "empty" { preferLocalBuild = true; } "mkdir -p $out";
-
- documentRootConf = ''
- DocumentRoot "${documentRoot}"
-
- <Directory "${documentRoot}">
- Options Indexes FollowSymLinks
- AllowOverride None
- ${allGranted}
- </Directory>
- '';
-
- robotsTxt =
- concatStringsSep "\n" (filter (x: x != "") (
- # If this is a vhost, the include the entries for the main server as well.
- (if isMainServer then [] else [mainCfg.robotsEntries] ++ map (svc: svc.robotsEntries) mainSubservices)
- ++ [cfg.robotsEntries]
- ++ (map (svc: svc.robotsEntries) subservices)));
-
- in ''
- ${concatStringsSep "\n" (map (n: "ServerName ${n}") serverInfo.canonicalNames)}
-
- ${concatMapStrings (alias: "ServerAlias ${alias}\n") cfg.serverAliases}
-
- ${if cfg.sslServerCert != null then ''
- SSLCertificateFile ${cfg.sslServerCert}
- SSLCertificateKeyFile ${cfg.sslServerKey}
- ${if cfg.sslServerChain != null then ''
- SSLCertificateChainFile ${cfg.sslServerChain}
- '' else ""}
- '' else ""}
-
- ${if cfg.enableSSL then ''
- SSLEngine on
- '' else if enableSSL then /* i.e., SSL is enabled for some host, but not this one */
- ''
- SSLEngine off
- '' else ""}
-
- ${if isMainServer || cfg.adminAddr != null then ''
- ServerAdmin ${cfg.adminAddr}
- '' else ""}
-
- ${if !isMainServer && mainCfg.logPerVirtualHost then ''
- ErrorLog ${mainCfg.logDir}/error-${cfg.hostName}.log
- CustomLog ${mainCfg.logDir}/access-${cfg.hostName}.log ${cfg.logFormat}
- '' else ""}
-
- ${optionalString (robotsTxt != "") ''
- Alias /robots.txt ${pkgs.writeText "robots.txt" robotsTxt}
- ''}
-
- ${if isMainServer || maybeDocumentRoot != null then documentRootConf else ""}
-
- ${if cfg.enableUserDir then ''
-
- UserDir public_html
- UserDir disabled root
-
- <Directory "/home/*/public_html">
- AllowOverride FileInfo AuthConfig Limit Indexes
- Options MultiViews Indexes SymLinksIfOwnerMatch IncludesNoExec
- <Limit GET POST OPTIONS>
- ${allGranted}
- </Limit>
- <LimitExcept GET POST OPTIONS>
- ${allDenied}
- </LimitExcept>
- </Directory>
-
- '' else ""}
-
- ${if cfg.globalRedirect != null && cfg.globalRedirect != "" then ''
- RedirectPermanent / ${cfg.globalRedirect}
- '' else ""}
-
- ${
- let makeFileConf = elem: ''
- Alias ${elem.urlPath} ${elem.file}
- '';
- in concatMapStrings makeFileConf cfg.servedFiles
- }
-
- ${
- let makeDirConf = elem: ''
- Alias ${elem.urlPath} ${elem.dir}/
- <Directory ${elem.dir}>
- Options +Indexes
- ${allGranted}
- AllowOverride All
- </Directory>
- '';
- in concatMapStrings makeDirConf cfg.servedDirs
- }
-
- ${concatMapStrings (svc: svc.extraConfig) subservices}
-
- ${cfg.extraConfig}
- '';
-
-
- confFile = pkgs.writeText "httpd.conf" ''
-
- ServerRoot ${httpd}
-
- ${optionalString version24 ''
- DefaultRuntimeDir ${mainCfg.stateDir}/runtime
- ''}
-
- PidFile ${mainCfg.stateDir}/httpd.pid
-
- ${optionalString (mainCfg.multiProcessingModule != "prefork") ''
- # mod_cgid requires this.
- ScriptSock ${mainCfg.stateDir}/cgisock
- ''}
-
- <IfModule prefork.c>
- MaxClients ${toString mainCfg.maxClients}
- MaxRequestsPerChild ${toString mainCfg.maxRequestsPerChild}
- </IfModule>
-
- ${let
- listen = concatMap getListen allHosts;
- toStr = listen: "Listen ${listenToString listen}\n";
- uniqueListen = uniqList {inputList = map toStr listen;};
- in concatStrings uniqueListen
- }
-
- User ${mainCfg.user}
- Group ${mainCfg.group}
-
- ${let
- load = {name, path}: "LoadModule ${name}_module ${path}\n";
- allModules =
- concatMap (svc: svc.extraModulesPre) allSubservices
- ++ map (name: {inherit name; path = "${httpd}/modules/mod_${name}.so";}) apacheModules
- ++ optional mainCfg.enableMellon { name = "auth_mellon"; path = "${pkgs.apacheHttpdPackages.mod_auth_mellon}/modules/mod_auth_mellon.so"; }
- ++ optional enablePHP { name = "php${phpMajorVersion}"; path = "${php}/modules/libphp${phpMajorVersion}.so"; }
- ++ optional enablePerl { name = "perl"; path = "${mod_perl}/modules/mod_perl.so"; }
- ++ concatMap (svc: svc.extraModules) allSubservices
- ++ extraForeignModules;
- in concatMapStrings load allModules
- }
-
- AddHandler type-map var
-
- <Files ~ "^\.ht">
- ${allDenied}
- </Files>
-
- ${mimeConf}
- ${loggingConf}
- ${browserHacks}
-
- Include ${httpd}/conf/extra/httpd-default.conf
- Include ${httpd}/conf/extra/httpd-autoindex.conf
- Include ${httpd}/conf/extra/httpd-multilang-errordoc.conf
- Include ${httpd}/conf/extra/httpd-languages.conf
-
- TraceEnable off
-
- ${if enableSSL then sslConf else ""}
-
- # Fascist default - deny access to everything.
- <Directory />
- Options FollowSymLinks
- AllowOverride None
- ${allDenied}
- </Directory>
-
- # Generate directives for the main server.
- ${perServerConf true mainCfg}
-
- # Always enable virtual hosts; it doesn't seem to hurt.
- ${let
- listen = concatMap getListen allHosts;
- uniqueListen = uniqList {inputList = listen;};
- directives = concatMapStrings (listen: "NameVirtualHost ${listenToString listen}\n") uniqueListen;
- in optionalString (!version24) directives
- }
-
- ${let
- makeVirtualHost = vhost: ''
- <VirtualHost ${concatStringsSep " " (map listenToString (getListen vhost))}>
- ${perServerConf false vhost}
- </VirtualHost>
- '';
- in concatMapStrings makeVirtualHost mainCfg.virtualHosts
- }
- '';
-
-
- enablePHP = mainCfg.enablePHP || any (svc: svc.enablePHP) allSubservices;
-
- enablePerl = mainCfg.enablePerl || any (svc: svc.enablePerl) allSubservices;
-
-
- # Generate the PHP configuration file. Should probably be factored
- # out into a separate module.
- phpIni = pkgs.runCommand "php.ini"
- { options = concatStringsSep "\n"
- ([ mainCfg.phpOptions ] ++ (map (svc: svc.phpOptions) allSubservices));
- preferLocalBuild = true;
- }
- ''
- cat ${php}/etc/php.ini > $out
- echo "$options" >> $out
- '';
-
-in
-
-
-{
-
- ###### interface
-
- options = {
-
- services.httpdProd = {
-
- enable = mkOption {
- type = types.bool;
- default = false;
- description = "Whether to enable the Apache HTTP Server.";
- };
-
- package = mkOption {
- type = types.package;
- default = pkgs.apacheHttpd;
- defaultText = "pkgs.apacheHttpd";
- description = ''
- Overridable attribute of the Apache HTTP Server package to use.
- '';
- };
-
- configFile = mkOption {
- type = types.path;
- default = confFile;
- defaultText = "confFile";
- example = literalExample ''pkgs.writeText "httpd.conf" "# my custom config file ..."'';
- description = ''
- Override the configuration file used by Apache. By default,
- NixOS generates one automatically.
- '';
- };
-
- extraConfig = mkOption {
- type = types.lines;
- default = "";
- description = ''
- Cnfiguration lines appended to the generated Apache
- configuration file. Note that this mechanism may not work
- when <option>configFile</option> is overridden.
- '';
- };
-
- extraModules = mkOption {
- type = types.listOf types.unspecified;
- default = [];
- example = literalExample ''[ "proxy_connect" { name = "php5"; path = "''${pkgs.php}/modules/libphp5.so"; } ]'';
- description = ''
- Additional Apache modules to be used. These can be
- specified as a string in the case of modules distributed
- with Apache, or as an attribute set specifying the
- <varname>name</varname> and <varname>path</varname> of the
- module.
- '';
- };
-
- logPerVirtualHost = mkOption {
- type = types.bool;
- default = false;
- description = ''
- If enabled, each virtual host gets its own
- <filename>access.log</filename> and
- <filename>error.log</filename>, namely suffixed by the
- <option>hostName</option> of the virtual host.
- '';
- };
-
- user = mkOption {
- type = types.str;
- default = "wwwrun";
- description = ''
- User account under which httpd runs. The account is created
- automatically if it doesn't exist.
- '';
- };
-
- group = mkOption {
- type = types.str;
- default = "wwwrun";
- description = ''
- Group under which httpd runs. The account is created
- automatically if it doesn't exist.
- '';
- };
-
- logDir = mkOption {
- type = types.path;
- default = "/var/log/httpd";
- description = ''
- Directory for Apache's log files. It is created automatically.
- '';
- };
-
- stateDir = mkOption {
- type = types.path;
- default = "/run/httpd";
- description = ''
- Directory for Apache's transient runtime state (such as PID
- files). It is created automatically. Note that the default,
- <filename>/run/httpd</filename>, is deleted at boot time.
- '';
- };
-
- virtualHosts = mkOption {
- type = types.listOf (types.submodule (
- { options = import <nixpkgs/nixos/modules/services/web-servers/apache-httpd/per-server-options.nix> {
- inherit lib;
- forMainServer = false;
- };
- }));
- default = [];
- example = [
- { hostName = "foo";
- documentRoot = "/data/webroot-foo";
- }
- { hostName = "bar";
- documentRoot = "/data/webroot-bar";
- }
- ];
- description = ''
- Specification of the virtual hosts served by Apache. Each
- element should be an attribute set specifying the
- configuration of the virtual host. The available options
- are the non-global options permissible for the main host.
- '';
- };
-
- enableMellon = mkOption {
- type = types.bool;
- default = false;
- description = "Whether to enable the mod_auth_mellon module.";
- };
-
- enablePHP = mkOption {
- type = types.bool;
- default = false;
- description = "Whether to enable the PHP module.";
- };
-
- phpPackage = mkOption {
- type = types.package;
- default = pkgs.php;
- defaultText = "pkgs.php";
- description = ''
- Overridable attribute of the PHP package to use.
- '';
- };
-
- enablePerl = mkOption {
- type = types.bool;
- default = false;
- description = "Whether to enable the Perl module (mod_perl).";
- };
-
- phpOptions = mkOption {
- type = types.lines;
- default = "";
- example =
- ''
- date.timezone = "CET"
- '';
- description =
- "Options appended to the PHP configuration file <filename>php.ini</filename>.";
- };
-
- multiProcessingModule = mkOption {
- type = types.str;
- default = "prefork";
- example = "worker";
- description =
- ''
- Multi-processing module to be used by Apache. Available
- modules are <literal>prefork</literal> (the default;
- handles each request in a separate child process),
- <literal>worker</literal> (hybrid approach that starts a
- number of child processes each running a number of
- threads) and <literal>event</literal> (a recent variant of
- <literal>worker</literal> that handles persistent
- connections more efficiently).
- '';
- };
-
- maxClients = mkOption {
- type = types.int;
- default = 150;
- example = 8;
- description = "Maximum number of httpd processes (prefork)";
- };
-
- maxRequestsPerChild = mkOption {
- type = types.int;
- default = 0;
- example = 500;
- description =
- "Maximum number of httpd requests answered per httpd child (prefork), 0 means unlimited";
- };
-
- sslCiphers = mkOption {
- type = types.str;
- default = "HIGH:!aNULL:!MD5:!EXP";
- description = "Cipher Suite available for negotiation in SSL proxy handshake.";
- };
-
- sslProtocols = mkOption {
- type = types.str;
- default = "All -SSLv2 -SSLv3 -TLSv1";
- example = "All -SSLv2 -SSLv3";
- description = "Allowed SSL/TLS protocol versions.";
- };
- }
-
- # Include the options shared between the main server and virtual hosts.
- // (import ./per-server-options.nix {
- inherit lib;
- forMainServer = true;
- });
-
- };
-
-
- ###### implementation
-
- config = mkIf config.services.httpdProd.enable {
-
- assertions = [ { assertion = mainCfg.enableSSL == true
- -> mainCfg.sslServerCert != null
- && mainCfg.sslServerKey != null;
- message = "SSL is enabled for httpd, but sslServerCert and/or sslServerKey haven't been specified."; }
- ];
-
- warnings = map (cfg: ''apache-httpd's port option is deprecated. Use listen = [{/*ip = "*"; */ port = ${toString cfg.port};}]; instead'' ) (lib.filter (cfg: cfg.port != 0) allHosts);
-
- environment.systemPackages = [httpd] ++ concatMap (svc: svc.extraPath) allSubservices;
-
- services.httpdProd.phpOptions =
- ''
- ; Needed for PHP's mail() function.
- sendmail_path = sendmail -t -i
-
- ; Don't advertise PHP
- expose_php = off
- '' + optionalString (!isNull config.time.timeZone) ''
-
- ; Apparently PHP doesn't use $TZ.
- date.timezone = "${config.time.timeZone}"
- '';
-
- systemd.services.httpdProd =
- { description = "Apache HTTPD";
-
- wantedBy = [ "multi-user.target" ];
- wants = [ "keys.target" ];
- after = [ "network.target" "fs.target" "postgresql.service" "keys.target" ];
-
- path =
- [ httpd pkgs.coreutils pkgs.gnugrep ]
- ++ optional enablePHP pkgs.system-sendmail # Needed for PHP's mail() function.
- ++ concatMap (svc: svc.extraServerPath) allSubservices;
-
- environment =
- optionalAttrs enablePHP { PHPRC = phpIni; }
- // optionalAttrs mainCfg.enableMellon { LD_LIBRARY_PATH = "${pkgs.xmlsec}/lib"; }
- // (listToAttrs (concatMap (svc: svc.globalEnvVars) allSubservices));
-
- preStart =
- ''
- mkdir -m 0750 -p ${mainCfg.stateDir}
- [ $(id -u) != 0 ] || chown root.${mainCfg.group} ${mainCfg.stateDir}
- ${optionalString version24 ''
- mkdir -m 0750 -p "${mainCfg.stateDir}/runtime"
- [ $(id -u) != 0 ] || chown root.${mainCfg.group} "${mainCfg.stateDir}/runtime"
- ''}
- mkdir -m 0700 -p ${mainCfg.logDir}
-
- # Get rid of old semaphores. These tend to accumulate across
- # server restarts, eventually preventing it from restarting
- # successfully.
- for i in $(${pkgs.utillinux}/bin/ipcs -s | grep ' ${mainCfg.user} ' | cut -f2 -d ' '); do
- ${pkgs.utillinux}/bin/ipcrm -s $i
- done
-
- # Run the startup hooks for the subservices.
- for i in ${toString (map (svn: svn.startupScript) allSubservices)}; do
- echo Running Apache startup hook $i...
- $i
- done
- '';
-
- serviceConfig.ExecStart = "@${httpd}/bin/httpd httpd -f ${httpdConf}";
- serviceConfig.ExecStop = "${httpd}/bin/httpd -f ${httpdConf} -k graceful-stop";
- serviceConfig.ExecReload = "${httpd}/bin/httpd -f ${httpdConf} -k graceful";
- serviceConfig.Type = "forking";
- serviceConfig.PIDFile = "${mainCfg.stateDir}/httpd.pid";
- serviceConfig.Restart = "always";
- serviceConfig.RestartSec = "5s";
- };
-
- };
-}
./tools/diaspora.nix
./tools/ether.nix
./tools/peertube.nix
- # built using:
- # sed -e "s/services\.httpd/services\.httpdProd/g" .nix-defexpr/channels/nixpkgs/nixos/modules/services/web-servers/apache-httpd/default.nix
- # Removed allGranted
- # And removed users / groups
- ./apache/httpd_prod.nix
- ./apache/httpd_inte.nix
- # except for this one for users/groups
- ./apache/httpd_tools.nix
# Adapted from base phpfpm
./phpfpm
];