Merge pull request #89773 from rnhmjoj/ncdns

ncdns: init at 0.0.10.3
This commit is contained in:
Michele Guerini Rocco 2020-07-07 10:58:55 +02:00 committed by GitHub
commit fc553c0bc5
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
8 changed files with 736 additions and 0 deletions

View file

@ -607,6 +607,7 @@
./services/networking/dnscrypt-wrapper.nix
./services/networking/dnsdist.nix
./services/networking/dnsmasq.nix
./services/networking/ncdns.nix
./services/networking/ejabberd.nix
./services/networking/epmd.nix
./services/networking/ergo.nix

View file

@ -0,0 +1,278 @@
{ config, lib, pkgs, ... }:
with lib;
let
cfgs = config.services;
cfg = cfgs.ncdns;
dataDir = "/var/lib/ncdns";
username = "ncdns";
valueType = with types; oneOf [ int str bool path ]
// { description = "setting type (integer, string, bool or path)"; };
configType = with types; attrsOf (nullOr (either valueType configType))
// { description = ''
ncdns.conf configuration type. The format consists of an
attribute set of settings. Each setting can be either `null`,
a value or an attribute set. The allowed values are integers,
strings, booleans or paths.
'';
};
configFile = pkgs.runCommand "ncdns.conf"
{ json = builtins.toJSON cfg.settings;
passAsFile = [ "json" ];
}
"${pkgs.remarshal}/bin/json2toml < $jsonPath > $out";
defaultFiles = {
public = "${dataDir}/bit.key";
private = "${dataDir}/bit.private";
zonePublic = "${dataDir}/bit-zone.key";
zonePrivate = "${dataDir}/bit-zone.private";
};
# if all keys are the default value
needsKeygen = all id (flip mapAttrsToList cfg.dnssec.keys
(n: v: v == getAttr n defaultFiles));
mkDefaultAttrs = mapAttrs (n: v: mkDefault v);
in
{
###### interface
options = {
services.ncdns = {
enable = mkEnableOption ''
ncdns, a Go daemon to bridge Namecoin to DNS.
To resolve .bit domains set <literal>services.namecoind.enable = true;</literal>
and an RPC username/password
'';
address = mkOption {
type = types.str;
default = "127.0.0.1";
description = ''
The IP address the ncdns resolver will bind to. Leave this unchanged
if you do not wish to directly expose the resolver.
'';
};
port = mkOption {
type = types.port;
default = 5333;
description = ''
The port the ncdns resolver will bind to.
'';
};
identity.hostname = mkOption {
type = types.str;
default = config.networking.hostName;
example = "example.com";
description = ''
The hostname of this ncdns instance, which defaults to the machine
hostname. If specified, ncdns lists the hostname as an NS record at
the zone apex:
<programlisting>
bit. IN NS ns1.example.com.
</programlisting>
If unset ncdns will generate an internal psuedo-hostname under the
zone, which will resolve to the value of
<option>services.ncdns.identity.address</option>.
If you are only using ncdns locally you can ignore this.
'';
};
identity.hostmaster = mkOption {
type = types.str;
default = "";
example = "root@example.com";
description = ''
An email address for the SOA record at the bit zone.
If you are only using ncdns locally you can ignore this.
'';
};
identity.address = mkOption {
type = types.str;
default = "127.127.127.127";
description = ''
The IP address the hostname specified in
<option>services.ncdns.identity.hostname</option> should resolve to.
If you are only using ncdns locally you can ignore this.
'';
};
dnssec.enable = mkEnableOption ''
DNSSEC support in ncdns. This will generate KSK and ZSK keypairs
(unless provided via the options
<option>services.ncdns.dnssec.publicKey</option>,
<option>services.ncdns.dnssec.privateKey</option> etc.) and add a trust
anchor to recursive resolvers
'';
dnssec.keys.public = mkOption {
type = types.path;
default = defaultFiles.public;
description = ''
Path to the file containing the KSK public key.
The key can be generated using the <literal>dnssec-keygen</literal>
command, provided by the package <package>bind</package> as follows:
<programlisting>
$ dnssec-keygen -a RSASHA256 -3 -b 2048 -f KSK bit
</programlisting>
'';
};
dnssec.keys.private = mkOption {
type = types.path;
default = defaultFiles.private;
description = ''
Path to the file containing the KSK private key.
'';
};
dnssec.keys.zonePublic = mkOption {
type = types.path;
default = defaultFiles.zonePublic;
description = ''
Path to the file containing the ZSK public key.
The key can be generated using the <literal>dnssec-keygen</literal>
command, provided by the package <package>bind</package> as follows:
<programlisting>
$ dnssec-keygen -a RSASHA256 -3 -b 2048 bit
</programlisting>
'';
};
dnssec.keys.zonePrivate = mkOption {
type = types.path;
default = defaultFiles.zonePrivate;
description = ''
Path to the file containing the ZSK private key.
'';
};
settings = mkOption {
type = configType;
default = { };
example = literalExample ''
{ # enable webserver
ncdns.httplistenaddr = ":8202";
# synchronize TLS certs
certstore.nss = true;
# note: all paths are relative to the config file
certstore.nsscertdir = "../../var/lib/ncdns";
certstore.nssdbdir = "../../home/alice/.pki/nssdb";
}
'';
description = ''
ncdns settings. Use this option to configure ncds
settings not exposed in a NixOS option or to bypass one.
See the example ncdns.conf file at <link xlink:href="
https://git.io/JfX7g"/> for the available options.
'';
};
};
services.pdns-recursor.resolveNamecoin = mkOption {
type = types.bool;
default = false;
description = ''
Resolve <literal>.bit</literal> top-level domains using ncdns and namecoin.
'';
};
};
###### implementation
config = mkIf cfg.enable {
services.pdns-recursor = mkIf cfgs.pdns-recursor.resolveNamecoin {
forwardZonesRecurse.bit = "127.0.0.1:${toString cfg.port}";
luaConfig =
if cfg.dnssec.enable
then ''readTrustAnchorsFromFile("${cfg.dnssec.keys.public}")''
else ''addNTA("bit", "namecoin DNSSEC disabled")'';
};
# Avoid pdns-recursor not finding the DNSSEC keys
systemd.services.pdns-recursor = mkIf cfgs.pdns-recursor.resolveNamecoin {
after = [ "ncdns.service" ];
wants = [ "ncdns.service" ];
};
services.ncdns.settings = mkDefaultAttrs {
ncdns =
{ # Namecoin RPC
namecoinrpcaddress =
"${cfgs.namecoind.rpc.address}:${toString cfgs.namecoind.rpc.port}";
namecoinrpcusername = cfgs.namecoind.rpc.user;
namecoinrpcpassword = cfgs.namecoind.rpc.password;
# Identity
selfname = cfg.identity.hostname;
hostmaster = cfg.identity.hostmaster;
selfip = cfg.identity.address;
# Other
bind = "${cfg.address}:${toString cfg.port}";
}
// optionalAttrs cfg.dnssec.enable
{ # DNSSEC
publickey = "../.." + cfg.dnssec.keys.public;
privatekey = "../.." + cfg.dnssec.keys.private;
zonepublickey = "../.." + cfg.dnssec.keys.zonePublic;
zoneprivatekey = "../.." + cfg.dnssec.keys.zonePrivate;
};
# Daemon
service.daemon = true;
xlog.journal = true;
};
users.users.ncdns =
{ description = "ncdns daemon user"; };
systemd.services.ncdns = {
description = "ncdns daemon";
after = [ "namecoind.service" ];
wantedBy = [ "multi-user.target" ];
serviceConfig = {
User = "ncdns";
StateDirectory = "ncdns";
Restart = "on-failure";
ExecStart = "${pkgs.ncdns}/bin/ncdns -conf=${configFile}";
};
preStart = optionalString (cfg.dnssec.enable && needsKeygen) ''
cd ${dataDir}
if [ ! -e bit.key ]; then
${pkgs.bind}/bin/dnssec-keygen -a RSASHA256 -3 -b 2048 bit
mv Kbit.*.key bit-zone.key
mv Kbit.*.private bit-zone.private
${pkgs.bind}/bin/dnssec-keygen -a RSASHA256 -3 -b 2048 -f KSK bit
mv Kbit.*.key bit.key
mv Kbit.*.private bit.private
fi
'';
};
};
meta.maintainers = with lib.maintainers; [ rnhmjoj ];
}

View file

@ -221,6 +221,7 @@ in
nat.firewall = handleTest ./nat.nix { withFirewall = true; };
nat.firewall-conntrack = handleTest ./nat.nix { withFirewall = true; withConntrackHelpers = true; };
nat.standalone = handleTest ./nat.nix { withFirewall = false; };
ncdns = handleTest ./ncdns.nix {};
ndppd = handleTest ./ndppd.nix {};
neo4j = handleTest ./neo4j.nix {};
specialisation = handleTest ./specialisation.nix {};

77
nixos/tests/ncdns.nix Normal file
View file

@ -0,0 +1,77 @@
import ./make-test-python.nix ({ pkgs, ... }:
let
fakeReply = pkgs.writeText "namecoin-reply.json" ''
{ "error": null,
"id": 1,
"result": {
"address": "T31q8ucJ4dI1xzhxQ5QispfECld5c7Xw",
"expired": false,
"expires_in": 2248,
"height": 438155,
"name": "d/test",
"txid": "db61c0b2540ba0c1a2c8cc92af703a37002e7566ecea4dbf8727c7191421edfb",
"value": "{\"ip\": \"1.2.3.4\", \"email\": \"root@test.bit\",\"info\": \"Fake record\"}",
"vout": 0
}
}
'';
in
{
name = "ncdns";
nodes.server = { ... }: {
networking.nameservers = [ "127.0.0.1" ];
services.namecoind.rpc = {
address = "127.0.0.1";
user = "namecoin";
password = "secret";
port = 8332;
};
# Fake namecoin RPC server because we can't
# run a full node in a test.
systemd.services.namecoind = {
wantedBy = [ "multi-user.target" ];
script = ''
while true; do
echo -e "HTTP/1.1 200 OK\n\n $(<${fakeReply})\n" \
| ${pkgs.netcat}/bin/nc -N -l 127.0.0.1 8332
done
'';
};
services.ncdns = {
enable = true;
dnssec.enable = true;
};
services.pdns-recursor = {
enable = true;
dns.allowFrom = [ "127.0.0.0/8" ];
settings.loglevel = 8;
resolveNamecoin = true;
};
environment.systemPackages = [ pkgs.dnsutils ];
};
testScript = ''
with subtest("DNSSEC keys have been generated"):
server.wait_for_unit("ncdns")
server.wait_for_file("/var/lib/ncdns/bit.key")
server.wait_for_file("/var/lib/ncdns/bit-zone.key")
with subtest("DNSKEY bit record is present"):
server.wait_for_unit("pdns-recursor")
server.wait_for_open_port("53")
server.succeed("host -t DNSKEY bit")
with subtest("can resolve a .bit name"):
server.wait_for_unit("namecoind")
server.wait_for_open_port("8332")
assert "1.2.3.4" in server.succeed("host -t A test.bit")
'';
})

View file

@ -0,0 +1,41 @@
{ lib, nixosTests, git, buildGoPackage, fetchFromGitHub, libcap }:
buildGoPackage rec {
pname = "ncdns";
version = "0.0.10.3";
goPackagePath = "github.com/namecoin/ncdns";
goDeps = ./deps.nix;
src = fetchFromGitHub {
owner = "namecoin";
repo = "ncdns";
rev = "v${version}";
sha256 = "12q5al48mkjhgyk7z5wyklzzrdbcqhwxl79axa4gh9ld75prghbq";
};
patches = [ ./fix-tpl-path.nix ];
buildInputs = [ libcap ];
preBuild = ''
go generate github.com/namecoin/x509-signature-splice/...
'';
postInstall = ''
mkdir -p "$out/share"
cp -r "$src/_doc" "$out/share/doc"
cp -r "$src/_tpl" "$out/share/tpl"
'';
meta = with lib; {
description = "Namecoin to DNS bridge daemon";
homepage = "https://github.com/namecoin/ncdns";
license = licenses.gpl3Plus;
platforms = platforms.all;
maintainers = with maintainers; [ rnhmjoj ];
};
passthru.tests.ncdns = nixosTests.ncdns;
}

309
pkgs/servers/dns/ncdns/deps.nix generated Normal file
View file

@ -0,0 +1,309 @@
# This file was generated by https://github.com/kamilchm/go2nix v1.3.0
[
{
goPackagePath = "github.com/BurntSushi/toml";
fetch = {
type = "git";
url = "https://github.com/BurntSushi/toml";
rev = "3012a1dbe2e4bd1391d42b32f0577cb7bbc7f005";
sha256 = "1fjdwwfzyzllgiwydknf1pwjvy49qxfsczqx5gz3y0izs7as99j6";
};
}
{
goPackagePath = "github.com/alecthomas/template";
fetch = {
type = "git";
url = "https://github.com/alecthomas/template";
rev = "fb15b899a75114aa79cc930e33c46b577cc664b1";
sha256 = "1vlasv4dgycydh5wx6jdcvz40zdv90zz1h7836z7lhsi2ymvii26";
};
}
{
goPackagePath = "github.com/alecthomas/units";
fetch = {
type = "git";
url = "https://github.com/alecthomas/units";
rev = "f65c72e2690dc4b403c8bd637baf4611cd4c069b";
sha256 = "04jyqm7m3m01ppfy1f9xk4qvrwvs78q9zml6llyf2b3v5k6b2bbc";
};
}
{
goPackagePath = "github.com/btcsuite/btcd";
fetch = {
type = "git";
url = "https://github.com/btcsuite/btcd";
rev = "9f0179fd2c46caba343b6515602cf37172f14d5f";
sha256 = "0cvpjsxlyzm04pwzi7nj43k9h5wfxj07jdc49qxsav5323v1nvka";
};
}
{
goPackagePath = "github.com/btcsuite/btclog";
fetch = {
type = "git";
url = "https://github.com/btcsuite/btclog";
rev = "84c8d2346e9fc8c7b947e243b9c24e6df9fd206a";
sha256 = "02dl46wcnfpg9sqvg0ipipkpnd7lrf4fnvb9zy56jqa7mfcwc7wk";
};
}
{
goPackagePath = "github.com/btcsuite/btcutil";
fetch = {
type = "git";
url = "https://github.com/btcsuite/btcutil";
rev = "b2bf7f89d674a3702182b7e15f52807896051af3";
sha256 = "0wwykb4cbq8xj2mls2mxma5vaahdgdy3vqw1r2fi4wyj0yr4kyw9";
};
}
{
goPackagePath = "github.com/btcsuite/go-socks";
fetch = {
type = "git";
url = "https://github.com/btcsuite/go-socks";
rev = "4720035b7bfd2a9bb130b1c184f8bbe41b6f0d0f";
sha256 = "18cv2icj059lq4s99p6yh91hlas5f2gi3f1p4c10sjgwrs933d7b";
};
}
{
goPackagePath = "github.com/btcsuite/websocket";
fetch = {
type = "git";
url = "https://github.com/btcsuite/websocket";
rev = "31079b6807923eb23992c421b114992b95131b55";
sha256 = "0xpkf257ml6fpfdgv7hxxc41n0d5yxxm3njm50qpzp7j71l9cjwa";
};
}
{
goPackagePath = "github.com/coreos/go-systemd";
fetch = {
type = "git";
url = "https://github.com/coreos/go-systemd";
rev = "b51e752dd1c9c618846f8bc5b95ab524bd7b11c2";
sha256 = "127dj1iwp69yj74nwh9ckgc0mkk1mv4yzbxmbdxix1r7j6q35z3j";
};
}
{
goPackagePath = "github.com/golang/groupcache";
fetch = {
type = "git";
url = "https://github.com/golang/groupcache";
rev = "8c9f03a8e57eb486e42badaed3fb287da51807ba";
sha256 = "0vjjr79r32icjzlb05wn02k59av7jx0rn1jijml8r4whlg7dnkfh";
};
}
{
goPackagePath = "github.com/hlandau/buildinfo";
fetch = {
type = "git";
url = "https://github.com/hlandau/buildinfo";
rev = "337a29b5499734e584d4630ce535af64c5fe7813";
sha256 = "1kq3r1i4rr9bcvj5yg8w1l95f6sfc3kn6kgcdmlh5i3j9w2sram8";
};
}
{
goPackagePath = "github.com/hlandau/degoutils";
fetch = {
type = "git";
url = "https://github.com/hlandau/degoutils";
rev = "8fa2440b63444dad556d76366f1c3ee070c8a577";
sha256 = "1yj39jbrk3xx3cyl8f4asakc74lsl0brasi25xjf6219pg69q0iy";
};
}
{
goPackagePath = "github.com/hlandau/dexlogconfig";
fetch = {
type = "git";
url = "https://github.com/hlandau/dexlogconfig";
rev = "244f29bd260884993b176cd14ef2f7631f6f3c18";
sha256 = "1d01ghx6xawj3nk3lpk51wbbpxdnc9vzvijvlayvp7cxgsacslbc";
};
}
{
goPackagePath = "github.com/hlandau/xlog";
fetch = {
type = "git";
url = "https://github.com/hlandau/xlog";
rev = "197ef798aed28e08ed3e176e678fda81be993a31";
sha256 = "08rjlqnjbfgpz5rbjq89l7y5vyhk99ivr928sqdi5gnqznbqs4m8";
};
}
{
goPackagePath = "github.com/kr/pretty";
fetch = {
type = "git";
url = "https://github.com/kr/pretty";
rev = "4e0886370c3a67530192c6a238cff68f56c141b0";
sha256 = "1ywbfzz1h3a3qd8rpkiqwi1dm4w8ls9ijb4x1b7567grns9f0vnp";
};
}
{
goPackagePath = "github.com/kr/text";
fetch = {
type = "git";
url = "https://github.com/kr/text";
rev = "702c74938df48b97370179f33ce2107bd7ff3b3e";
sha256 = "0hf58ypz6rxsw6nx3i856whir9lvy4sdx946wbw1nfaf2rdmr9vx";
};
}
{
goPackagePath = "github.com/mattn/go-isatty";
fetch = {
type = "git";
url = "https://github.com/mattn/go-isatty";
rev = "cb30d6282491c185f77d9bec5d25de1bb61a06bc";
sha256 = "0v59mv94acd2m72q8adhigxkx1vn38l5h0d8hp0nxga2v9f3v8kd";
};
}
{
goPackagePath = "github.com/miekg/dns";
fetch = {
type = "git";
url = "https://github.com/miekg/dns";
rev = "203ad2480beb9330454efc215d21f16c607e8174";
sha256 = "12i2l79whv7a8c27f1dvq4wqikx4d0l30r1ja68zfgrgik6vryxq";
};
}
{
goPackagePath = "github.com/namecoin/btcd";
fetch = {
type = "git";
url = "https://github.com/namecoin/btcd";
rev = "69a10543311fa68737d0a77b4cd045b0b0abfb75";
sha256 = "1zbfigs3hrjhdwp19877lpgivdcz3k80149nxdmxlmp03xcswcqy";
};
}
{
goPackagePath = "github.com/namecoin/ncbtcjson";
fetch = {
type = "git";
url = "https://github.com/namecoin/ncbtcjson";
rev = "fa221af062c70f802db6ed66e1546cc4a41ec277";
sha256 = "1fmz5aylsji27vj5f3f3gg9xj99735gh5prvcfz0gmk68v1mnr4i";
};
}
{
goPackagePath = "github.com/namecoin/ncrpcclient";
fetch = {
type = "git";
url = "https://github.com/namecoin/ncrpcclient";
rev = "858e1a5acd8b2da56462f50323633cdf2fe80977";
sha256 = "0pj951wm6fdkk2yv4bxaxka52i7rb6w3fs9ah3fy7p8wchr4smjx";
};
}
{
goPackagePath = "github.com/namecoin/tlsrestrictnss";
fetch = {
type = "git";
url = "https://github.com/namecoin/tlsrestrictnss";
rev = "945a9f3d995fcb175fd0b19549e21a3e87ba8c13";
sha256 = "18qphkqnjw3bwflkyyrddyzgwscs37j7y6ynm9g78bqb5skviqqy";
};
}
{
goPackagePath = "github.com/namecoin/x509-signature-splice";
fetch = {
type = "git";
url = "https://github.com/namecoin/x509-signature-splice";
rev = "d8b4bf2df701c55239a9fe82bb1e7bea10e30599";
sha256 = "0jlj4gb60s7b69d8yx6ljhxgvqgjz01n0h59fswblw09wfba8c4j";
};
}
{
goPackagePath = "github.com/ogier/pflag";
fetch = {
type = "git";
url = "https://github.com/ogier/pflag";
rev = "45c278ab3607870051a2ea9040bb85fcb8557481";
sha256 = "0620v75wppfd84d95n312wpngcb73cph4q3ivs1h0waljfnsrd5l";
};
}
{
goPackagePath = "github.com/shiena/ansicolor";
fetch = {
type = "git";
url = "https://github.com/shiena/ansicolor";
rev = "a422bbe96644373c5753384a59d678f7d261ff10";
sha256 = "1dcn8a9z6a5dxa2m3fkppnajcls8lanbl38qggkf646yi5qsk1hc";
};
}
{
goPackagePath = "golang.org/x/crypto";
fetch = {
type = "git";
url = "https://go.googlesource.com/crypto";
rev = "279210d13fedf5be6d476bad5df6a015042bb905";
sha256 = "0syi72jba84nn1z89bqpcv94wjvzj71dwg1pj30xrcixcz1zsg26";
};
}
{
goPackagePath = "golang.org/x/net";
fetch = {
type = "git";
url = "https://go.googlesource.com/net";
rev = "627f9648deb96c27737b83199d44bb5c1010cbcf";
sha256 = "0ziz7i9mhz6dy2f58dsa83flkk165w1cnazm7yksql5i9m7x099z";
};
}
{
goPackagePath = "golang.org/x/sys";
fetch = {
type = "git";
url = "https://go.googlesource.com/sys";
rev = "6fdc65e7d9800cc59998e8ac0d9406a20ff5f399";
sha256 = "0al5gzij4qkrp11i1h8j7288pg6y716zyh2v0886pv2knha7gjvj";
};
}
{
goPackagePath = "gopkg.in/alecthomas/kingpin.v2";
fetch = {
type = "git";
url = "https://gopkg.in/alecthomas/kingpin.v2";
rev = "947dcec5ba9c011838740e680966fd7087a71d0d";
sha256 = "0mndnv3hdngr3bxp7yxfd47cas4prv98sqw534mx7vp38gd88n5r";
};
}
{
goPackagePath = "gopkg.in/hlandau/configurable.v1";
fetch = {
type = "git";
url = "https://gopkg.in/hlandau/configurable.v1";
rev = "41496864a1fe3e0fef2973f22372b755d2897402";
sha256 = "0i9jbdvi8rz12xsrzzbfxg5lwsqakjcmccsa5a32asmv26k5byqa";
};
}
{
goPackagePath = "gopkg.in/hlandau/easyconfig.v1";
fetch = {
type = "git";
url = "https://gopkg.in/hlandau/easyconfig.v1";
rev = "c31249162931b4963bbe6e501cccb60d23271a3f";
sha256 = "1v8j1pyzcfj1l4pmb1c6mszci6xzc4agdam2kq79kyvbsvbbw9dc";
};
}
{
goPackagePath = "gopkg.in/hlandau/madns.v2";
fetch = {
type = "git";
url = "https://gopkg.in/hlandau/madns.v2";
rev = "26979b3e4b5aa3e0bd53cf0a014f9eaf43b578e3";
sha256 = "09r4m4mqdgd7hvxyvss9m64lq0kk8nylnq2bgnkrclgzpi87fmmb";
};
}
{
goPackagePath = "gopkg.in/hlandau/service.v2";
fetch = {
type = "git";
url = "https://gopkg.in/hlandau/service.v2";
rev = "b64b3467ebd16f64faec1640c25e318efc0c0d7b";
sha256 = "0lpx88f46ylx9lf6jgwcjgklll1pc1mlakrywpa0wzhjj7a4jinc";
};
}
{
goPackagePath = "gopkg.in/hlandau/svcutils.v1";
fetch = {
type = "git";
url = "https://gopkg.in/hlandau/svcutils.v1";
rev = "c25dac49e50cbbcbef8c81b089f56156f4067729";
sha256 = "12b6p71mk33r44d71xizjq82fls0ykfwfl5gnmckbgpxms4bj2xf";
};
}
]

View file

@ -0,0 +1,27 @@
This sets a default value for the tpl directory that works for Nixpkgs.
diff --git a/server/web.go b/server/web.go
index d024a42..0522d02 100644
--- a/server/web.go
+++ b/server/web.go
@@ -10,6 +10,7 @@ import "path/filepath"
import "time"
import "strings"
import "fmt"
+import "os"
var layoutTpl *template.Template
var mainPageTpl *template.Template
@@ -44,7 +45,11 @@ func deriveTemplate(filename string) (*template.Template, error) {
}
func (s *Server) tplFilename(filename string) string {
- td := filepath.Join(s.cfg.ConfigDir, "..", "tpl")
+ ex, err := os.Executable()
+ if err != nil {
+ panic(err)
+ }
+ td := filepath.Join(filepath.Dir(ex), "..", "share", "tpl")
if s.cfg.TplPath != "" {
td = s.cfg.TplPath
}

View file

@ -16012,6 +16012,8 @@ in
unit = callPackage ../servers/http/unit { };
ncdns = callPackage ../servers/dns/ncdns { };
nginx = nginxStable;
nginxStable = callPackage ../servers/http/nginx/stable.nix {