feat: use treefmt-nix and split up flake.nix
This commit is contained in:
parent
442601f25a
commit
c81d7af356
8 changed files with 284 additions and 256 deletions
32
flake-modules/default.nix
Normal file
32
flake-modules/default.nix
Normal file
|
@ -0,0 +1,32 @@
|
||||||
|
{ inputs, ... }:
|
||||||
|
{
|
||||||
|
imports = [
|
||||||
|
inputs.treefmt-nix.flakeModule
|
||||||
|
./package.nix
|
||||||
|
./overlay.nix
|
||||||
|
./module.nix
|
||||||
|
];
|
||||||
|
|
||||||
|
perSystem =
|
||||||
|
{ pkgs, ... }:
|
||||||
|
{
|
||||||
|
# Setup formatters
|
||||||
|
treefmt = {
|
||||||
|
projectRootFile = "flake.nix";
|
||||||
|
programs = {
|
||||||
|
nixfmt.enable = true;
|
||||||
|
rustfmt.enable = true;
|
||||||
|
statix.enable = true;
|
||||||
|
typos.enable = true;
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
devShells.default = pkgs.mkShellNoCC {
|
||||||
|
packages = [
|
||||||
|
pkgs.cargo-insta
|
||||||
|
pkgs.cargo-udeps
|
||||||
|
pkgs.mold
|
||||||
|
];
|
||||||
|
};
|
||||||
|
};
|
||||||
|
}
|
196
flake-modules/module.nix
Normal file
196
flake-modules/module.nix
Normal file
|
@ -0,0 +1,196 @@
|
||||||
|
let
|
||||||
|
module =
|
||||||
|
{
|
||||||
|
lib,
|
||||||
|
pkgs,
|
||||||
|
config,
|
||||||
|
...
|
||||||
|
}:
|
||||||
|
let
|
||||||
|
cfg = config.services.webnsupdate;
|
||||||
|
inherit (lib)
|
||||||
|
mkOption
|
||||||
|
mkEnableOption
|
||||||
|
mkPackageOption
|
||||||
|
types
|
||||||
|
;
|
||||||
|
in
|
||||||
|
{
|
||||||
|
options.services.webnsupdate = mkOption {
|
||||||
|
description = "An HTTP server for nsupdate.";
|
||||||
|
default = { };
|
||||||
|
type = types.submodule {
|
||||||
|
options = {
|
||||||
|
enable = mkEnableOption "webnsupdate";
|
||||||
|
extraArgs = mkOption {
|
||||||
|
description = ''
|
||||||
|
Extra arguments to be passed to the webnsupdate server command.
|
||||||
|
'';
|
||||||
|
type = types.listOf types.str;
|
||||||
|
default = [ ];
|
||||||
|
example = [ "--ip-source" ];
|
||||||
|
};
|
||||||
|
package = mkPackageOption pkgs "webnsupdate" { };
|
||||||
|
bindIp = mkOption {
|
||||||
|
description = ''
|
||||||
|
IP address to bind to.
|
||||||
|
|
||||||
|
Setting it to anything other than localhost is very insecure as
|
||||||
|
`webnsupdate` only supports plain HTTP and should always be behind a
|
||||||
|
reverse proxy.
|
||||||
|
'';
|
||||||
|
type = types.str;
|
||||||
|
default = "localhost";
|
||||||
|
example = "0.0.0.0";
|
||||||
|
};
|
||||||
|
bindPort = mkOption {
|
||||||
|
description = "Port to bind to.";
|
||||||
|
type = types.port;
|
||||||
|
default = 5353;
|
||||||
|
};
|
||||||
|
passwordFile = mkOption {
|
||||||
|
description = ''
|
||||||
|
The file where the password is stored.
|
||||||
|
|
||||||
|
This file can be created by running `webnsupdate mkpasswd $USERNAME $PASSWORD`.
|
||||||
|
'';
|
||||||
|
type = types.path;
|
||||||
|
example = "/secrets/webnsupdate.pass";
|
||||||
|
};
|
||||||
|
keyFile = mkOption {
|
||||||
|
description = ''
|
||||||
|
The TSIG key that `nsupdate` should use.
|
||||||
|
|
||||||
|
This file will be passed to `nsupdate` through the `-k` option, so look
|
||||||
|
at `man 8 nsupdate` for information on the key's format.
|
||||||
|
'';
|
||||||
|
type = types.path;
|
||||||
|
example = "/secrets/webnsupdate.key";
|
||||||
|
};
|
||||||
|
ttl = mkOption {
|
||||||
|
description = "The TTL that should be set on the zone records created by `nsupdate`.";
|
||||||
|
type = types.ints.positive;
|
||||||
|
default = 60;
|
||||||
|
example = 3600;
|
||||||
|
};
|
||||||
|
records = mkOption {
|
||||||
|
description = ''
|
||||||
|
The fqdn of records that should be updated.
|
||||||
|
|
||||||
|
Empty lines will be ignored, but whitespace will not be.
|
||||||
|
'';
|
||||||
|
type = types.nullOr types.lines;
|
||||||
|
default = null;
|
||||||
|
example = ''
|
||||||
|
example.com.
|
||||||
|
|
||||||
|
example.org.
|
||||||
|
ci.example.org.
|
||||||
|
'';
|
||||||
|
};
|
||||||
|
recordsFile = mkOption {
|
||||||
|
description = ''
|
||||||
|
The fqdn of records that should be updated.
|
||||||
|
|
||||||
|
Empty lines will be ignored, but whitespace will not be.
|
||||||
|
'';
|
||||||
|
type = types.nullOr types.path;
|
||||||
|
default = null;
|
||||||
|
example = "/secrets/webnsupdate.records";
|
||||||
|
};
|
||||||
|
user = mkOption {
|
||||||
|
description = "The user to run as.";
|
||||||
|
type = types.str;
|
||||||
|
default = "named";
|
||||||
|
};
|
||||||
|
group = mkOption {
|
||||||
|
description = "The group to run as.";
|
||||||
|
type = types.str;
|
||||||
|
default = "named";
|
||||||
|
};
|
||||||
|
};
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
config =
|
||||||
|
let
|
||||||
|
recordsFile =
|
||||||
|
if cfg.recordsFile != null then cfg.recordsFile else pkgs.writeText "webnsrecords" cfg.records;
|
||||||
|
args = lib.strings.escapeShellArgs (
|
||||||
|
[
|
||||||
|
"--records"
|
||||||
|
recordsFile
|
||||||
|
"--key-file"
|
||||||
|
cfg.keyFile
|
||||||
|
"--password-file"
|
||||||
|
cfg.passwordFile
|
||||||
|
"--address"
|
||||||
|
cfg.bindIp
|
||||||
|
"--port"
|
||||||
|
(builtins.toString cfg.bindPort)
|
||||||
|
"--ttl"
|
||||||
|
(builtins.toString cfg.ttl)
|
||||||
|
"--data-dir=%S/webnsupdate"
|
||||||
|
]
|
||||||
|
++ cfg.extraArgs
|
||||||
|
);
|
||||||
|
cmd = "${lib.getExe cfg.package} ${args}";
|
||||||
|
in
|
||||||
|
lib.mkIf cfg.enable {
|
||||||
|
# warnings =
|
||||||
|
# lib.optional (!config.services.bind.enable) "`webnsupdate` is expected to be used alongside `bind`. This is an unsopported configuration.";
|
||||||
|
assertions = [
|
||||||
|
{
|
||||||
|
assertion =
|
||||||
|
(cfg.records != null || cfg.recordsFile != null)
|
||||||
|
&& !(cfg.records != null && cfg.recordsFile != null);
|
||||||
|
message = "Exactly one of `services.webnsupdate.records` and `services.webnsupdate.recordsFile` must be set.";
|
||||||
|
}
|
||||||
|
];
|
||||||
|
|
||||||
|
systemd.services.webnsupdate = {
|
||||||
|
description = "Web interface for nsupdate.";
|
||||||
|
wantedBy = [ "multi-user.target" ];
|
||||||
|
after = [
|
||||||
|
"network.target"
|
||||||
|
"bind.service"
|
||||||
|
];
|
||||||
|
preStart = "${cmd} verify";
|
||||||
|
path = [ pkgs.dig ];
|
||||||
|
startLimitIntervalSec = 60;
|
||||||
|
serviceConfig = {
|
||||||
|
ExecStart = [ cmd ];
|
||||||
|
Type = "exec";
|
||||||
|
Restart = "on-failure";
|
||||||
|
RestartSec = "10s";
|
||||||
|
# User and group
|
||||||
|
User = cfg.user;
|
||||||
|
Group = cfg.group;
|
||||||
|
# Runtime directory and mode
|
||||||
|
RuntimeDirectory = "webnsupdate";
|
||||||
|
RuntimeDirectoryMode = "0750";
|
||||||
|
# Cache directory and mode
|
||||||
|
CacheDirectory = "webnsupdate";
|
||||||
|
CacheDirectoryMode = "0750";
|
||||||
|
# Logs directory and mode
|
||||||
|
LogsDirectory = "webnsupdate";
|
||||||
|
LogsDirectoryMode = "0750";
|
||||||
|
# State directory and mode
|
||||||
|
StateDirectory = "webnsupdate";
|
||||||
|
StateDirectoryMode = "0750";
|
||||||
|
# New file permissions
|
||||||
|
UMask = "0027";
|
||||||
|
# Security
|
||||||
|
NoNewPrivileges = true;
|
||||||
|
ProtectHome = true;
|
||||||
|
};
|
||||||
|
};
|
||||||
|
};
|
||||||
|
};
|
||||||
|
in
|
||||||
|
{
|
||||||
|
flake.nixosModules = {
|
||||||
|
default = module;
|
||||||
|
webnsupdate = module;
|
||||||
|
};
|
||||||
|
}
|
5
flake-modules/overlay.nix
Normal file
5
flake-modules/overlay.nix
Normal file
|
@ -0,0 +1,5 @@
|
||||||
|
{
|
||||||
|
flake = {
|
||||||
|
overlays.default = _final: prev: { webnsupdate = prev.callPackage ../default.nix { }; };
|
||||||
|
};
|
||||||
|
}
|
24
flake-modules/package.nix
Normal file
24
flake-modules/package.nix
Normal file
|
@ -0,0 +1,24 @@
|
||||||
|
{
|
||||||
|
perSystem =
|
||||||
|
{ pkgs, ... }:
|
||||||
|
{
|
||||||
|
packages =
|
||||||
|
let
|
||||||
|
webnsupdate = pkgs.callPackage ../default.nix { };
|
||||||
|
in
|
||||||
|
{
|
||||||
|
inherit webnsupdate;
|
||||||
|
default = webnsupdate;
|
||||||
|
cargo-update = pkgs.writeShellApplication {
|
||||||
|
name = "cargo-update-lockfile";
|
||||||
|
runtimeInputs = with pkgs; [
|
||||||
|
cargo
|
||||||
|
gnused
|
||||||
|
];
|
||||||
|
text = ''
|
||||||
|
CARGO_TERM_COLOR=never cargo update 2>&1 | sed '/crates.io index/d' | tee -a cargo_update.log
|
||||||
|
'';
|
||||||
|
};
|
||||||
|
};
|
||||||
|
};
|
||||||
|
}
|
23
flake.lock
23
flake.lock
|
@ -39,7 +39,8 @@
|
||||||
"inputs": {
|
"inputs": {
|
||||||
"flake-parts": "flake-parts",
|
"flake-parts": "flake-parts",
|
||||||
"nixpkgs": "nixpkgs",
|
"nixpkgs": "nixpkgs",
|
||||||
"systems": "systems"
|
"systems": "systems",
|
||||||
|
"treefmt-nix": "treefmt-nix"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"systems": {
|
"systems": {
|
||||||
|
@ -56,6 +57,26 @@
|
||||||
"repo": "default",
|
"repo": "default",
|
||||||
"type": "github"
|
"type": "github"
|
||||||
}
|
}
|
||||||
|
},
|
||||||
|
"treefmt-nix": {
|
||||||
|
"inputs": {
|
||||||
|
"nixpkgs": [
|
||||||
|
"nixpkgs"
|
||||||
|
]
|
||||||
|
},
|
||||||
|
"locked": {
|
||||||
|
"lastModified": 1729613947,
|
||||||
|
"narHash": "sha256-XGOvuIPW1XRfPgHtGYXd5MAmJzZtOuwlfKDgxX5KT3s=",
|
||||||
|
"owner": "numtide",
|
||||||
|
"repo": "treefmt-nix",
|
||||||
|
"rev": "aac86347fb5063960eccb19493e0cadcdb4205ca",
|
||||||
|
"type": "github"
|
||||||
|
},
|
||||||
|
"original": {
|
||||||
|
"owner": "numtide",
|
||||||
|
"repo": "treefmt-nix",
|
||||||
|
"type": "github"
|
||||||
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"root": "root",
|
"root": "root",
|
||||||
|
|
67
flake.nix
67
flake.nix
|
@ -7,73 +7,16 @@
|
||||||
url = "github:hercules-ci/flake-parts";
|
url = "github:hercules-ci/flake-parts";
|
||||||
inputs.nixpkgs-lib.follows = "nixpkgs";
|
inputs.nixpkgs-lib.follows = "nixpkgs";
|
||||||
};
|
};
|
||||||
|
treefmt-nix = {
|
||||||
|
url = "github:numtide/treefmt-nix";
|
||||||
|
inputs.nixpkgs.follows = "nixpkgs";
|
||||||
|
};
|
||||||
};
|
};
|
||||||
|
|
||||||
outputs =
|
outputs =
|
||||||
inputs:
|
inputs:
|
||||||
inputs.flake-parts.lib.mkFlake { inherit inputs; } {
|
inputs.flake-parts.lib.mkFlake { inherit inputs; } {
|
||||||
|
imports = [ ./flake-modules ];
|
||||||
systems = import inputs.systems;
|
systems = import inputs.systems;
|
||||||
perSystem =
|
|
||||||
{
|
|
||||||
lib,
|
|
||||||
pkgs,
|
|
||||||
self',
|
|
||||||
...
|
|
||||||
}:
|
|
||||||
{
|
|
||||||
packages =
|
|
||||||
let
|
|
||||||
webnsupdate = pkgs.callPackage ./default.nix { };
|
|
||||||
in
|
|
||||||
{
|
|
||||||
inherit webnsupdate;
|
|
||||||
default = webnsupdate;
|
|
||||||
cargo-update = pkgs.writeShellApplication {
|
|
||||||
name = "cargo-update-lockfile";
|
|
||||||
runtimeInputs = with pkgs; [
|
|
||||||
cargo
|
|
||||||
gnused
|
|
||||||
];
|
|
||||||
text = ''
|
|
||||||
CARGO_TERM_COLOR=never cargo update 2>&1 | sed '/crates.io index/d' | tee -a cargo_update.log
|
|
||||||
'';
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
formatter = pkgs.nixfmt-rfc-style;
|
|
||||||
|
|
||||||
checks = {
|
|
||||||
fmtRust = pkgs.callPackage ./run-cmd.nix {
|
|
||||||
src = inputs.self;
|
|
||||||
name = "fmt-rust";
|
|
||||||
extraNativeBuildInputs = [ pkgs.rustfmt ];
|
|
||||||
cmd = "${lib.getExe pkgs.cargo} fmt --all --check --verbose";
|
|
||||||
};
|
|
||||||
fmtNix = pkgs.callPackage ./run-cmd.nix {
|
|
||||||
src = inputs.self;
|
|
||||||
name = "fmt-nix";
|
|
||||||
cmd = "${lib.getExe self'.formatter} --check .";
|
|
||||||
};
|
|
||||||
lintNix = pkgs.callPackage ./run-cmd.nix {
|
|
||||||
src = inputs.self;
|
|
||||||
name = "lint-nix";
|
|
||||||
cmd = "${lib.getExe pkgs.statix} check .";
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
devShells.default = pkgs.mkShell {
|
|
||||||
packages = [
|
|
||||||
pkgs.cargo-insta
|
|
||||||
pkgs.cargo-udeps
|
|
||||||
pkgs.mold
|
|
||||||
];
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
flake = {
|
|
||||||
overlays.default = final: prev: { webnsupdate = final.callPackage ./default.nix { }; };
|
|
||||||
|
|
||||||
nixosModules.default = ./module.nix;
|
|
||||||
};
|
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
177
module.nix
177
module.nix
|
@ -1,177 +0,0 @@
|
||||||
{
|
|
||||||
lib,
|
|
||||||
pkgs,
|
|
||||||
config,
|
|
||||||
...
|
|
||||||
}:
|
|
||||||
let
|
|
||||||
cfg = config.services.webnsupdate;
|
|
||||||
inherit (lib) mkOption mkEnableOption types;
|
|
||||||
in
|
|
||||||
{
|
|
||||||
options.services.webnsupdate = mkOption {
|
|
||||||
description = "An HTTP server for nsupdate.";
|
|
||||||
default = { };
|
|
||||||
type = types.submodule {
|
|
||||||
options = {
|
|
||||||
enable = mkEnableOption "webnsupdate";
|
|
||||||
extraArgs = mkOption {
|
|
||||||
description = ''
|
|
||||||
Extra arguments to be passed to the webnsupdate server command.
|
|
||||||
'';
|
|
||||||
type = types.listOf types.str;
|
|
||||||
default = [ ];
|
|
||||||
example = [ "--ip-source" ];
|
|
||||||
};
|
|
||||||
bindIp = mkOption {
|
|
||||||
description = ''
|
|
||||||
IP address to bind to.
|
|
||||||
|
|
||||||
Setting it to anything other than localhost is very insecure as
|
|
||||||
`webnsupdate` only supports plain HTTP and should always be behind a
|
|
||||||
reverse proxy.
|
|
||||||
'';
|
|
||||||
type = types.str;
|
|
||||||
default = "localhost";
|
|
||||||
example = "0.0.0.0";
|
|
||||||
};
|
|
||||||
bindPort = mkOption {
|
|
||||||
description = "Port to bind to.";
|
|
||||||
type = types.port;
|
|
||||||
default = 5353;
|
|
||||||
};
|
|
||||||
passwordFile = mkOption {
|
|
||||||
description = ''
|
|
||||||
The file where the password is stored.
|
|
||||||
|
|
||||||
This file can be created by running `webnsupdate mkpasswd $USERNAME $PASSWORD`.
|
|
||||||
'';
|
|
||||||
type = types.path;
|
|
||||||
example = "/secrets/webnsupdate.pass";
|
|
||||||
};
|
|
||||||
keyFile = mkOption {
|
|
||||||
description = ''
|
|
||||||
The TSIG key that `nsupdate` should use.
|
|
||||||
|
|
||||||
This file will be passed to `nsupdate` through the `-k` option, so look
|
|
||||||
at `man 8 nsupdate` for information on the key's format.
|
|
||||||
'';
|
|
||||||
type = types.path;
|
|
||||||
example = "/secrets/webnsupdate.key";
|
|
||||||
};
|
|
||||||
ttl = mkOption {
|
|
||||||
description = "The TTL that should be set on the zone records created by `nsupdate`.";
|
|
||||||
type = types.ints.positive;
|
|
||||||
default = 60;
|
|
||||||
example = 3600;
|
|
||||||
};
|
|
||||||
records = mkOption {
|
|
||||||
description = ''
|
|
||||||
The fqdn of records that should be updated.
|
|
||||||
|
|
||||||
Empty lines will be ignored, but whitespace will not be.
|
|
||||||
'';
|
|
||||||
type = types.nullOr types.lines;
|
|
||||||
default = null;
|
|
||||||
example = ''
|
|
||||||
example.com.
|
|
||||||
|
|
||||||
example.org.
|
|
||||||
ci.example.org.
|
|
||||||
'';
|
|
||||||
};
|
|
||||||
recordsFile = mkOption {
|
|
||||||
description = ''
|
|
||||||
The fqdn of records that should be updated.
|
|
||||||
|
|
||||||
Empty lines will be ignored, but whitespace will not be.
|
|
||||||
'';
|
|
||||||
type = types.nullOr types.path;
|
|
||||||
default = null;
|
|
||||||
example = "/secrets/webnsupdate.records";
|
|
||||||
};
|
|
||||||
user = mkOption {
|
|
||||||
description = "The user to run as.";
|
|
||||||
type = types.str;
|
|
||||||
default = "named";
|
|
||||||
};
|
|
||||||
group = mkOption {
|
|
||||||
description = "The group to run as.";
|
|
||||||
type = types.str;
|
|
||||||
default = "named";
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
config =
|
|
||||||
let
|
|
||||||
recordsFile =
|
|
||||||
if cfg.recordsFile != null then cfg.recordsFile else pkgs.writeText "webnsrecords" cfg.records;
|
|
||||||
args = lib.strings.escapeShellArgs (
|
|
||||||
[
|
|
||||||
"--records"
|
|
||||||
recordsFile
|
|
||||||
"--key-file"
|
|
||||||
cfg.keyFile
|
|
||||||
"--password-file"
|
|
||||||
cfg.passwordFile
|
|
||||||
"--address"
|
|
||||||
cfg.bindIp
|
|
||||||
"--port"
|
|
||||||
(builtins.toString cfg.bindPort)
|
|
||||||
"--ttl"
|
|
||||||
(builtins.toString cfg.ttl)
|
|
||||||
]
|
|
||||||
++ cfg.extraArgs
|
|
||||||
);
|
|
||||||
cmd = "${lib.getExe pkgs.webnsupdate} ${args}";
|
|
||||||
in
|
|
||||||
lib.mkIf cfg.enable {
|
|
||||||
# warnings =
|
|
||||||
# lib.optional (!config.services.bind.enable) "`webnsupdate` is expected to be used alongside `bind`. This is an unsopported configuration.";
|
|
||||||
assertions = [
|
|
||||||
{
|
|
||||||
assertion =
|
|
||||||
(cfg.records != null || cfg.recordsFile != null)
|
|
||||||
&& !(cfg.records != null && cfg.recordsFile != null);
|
|
||||||
message = "Exactly one of `services.webnsupdate.records` and `services.webnsupdate.recordsFile` must be set.";
|
|
||||||
}
|
|
||||||
];
|
|
||||||
|
|
||||||
systemd.services.webnsupdate = {
|
|
||||||
description = "Web interface for nsupdate.";
|
|
||||||
wantedBy = [ "multi-user.target" ];
|
|
||||||
after = [
|
|
||||||
"network.target"
|
|
||||||
"bind.service"
|
|
||||||
];
|
|
||||||
preStart = "${cmd} verify";
|
|
||||||
path = [ pkgs.dig ];
|
|
||||||
startLimitIntervalSec = 60;
|
|
||||||
serviceConfig = {
|
|
||||||
ExecStart = [ cmd ];
|
|
||||||
Type = "exec";
|
|
||||||
Restart = "on-failure";
|
|
||||||
RestartSec = "10s";
|
|
||||||
# User and group
|
|
||||||
User = cfg.user;
|
|
||||||
Group = cfg.group;
|
|
||||||
# Runtime directory and mode
|
|
||||||
RuntimeDirectory = "webnsupdate";
|
|
||||||
RuntimeDirectoryMode = "0750";
|
|
||||||
# Cache directory and mode
|
|
||||||
CacheDirectory = "webnsupdate";
|
|
||||||
CacheDirectoryMode = "0750";
|
|
||||||
# Logs directory and mode
|
|
||||||
LogsDirectory = "webnsupdate";
|
|
||||||
LogsDirectoryMode = "0750";
|
|
||||||
# New file permissions
|
|
||||||
UMask = "0027";
|
|
||||||
# Security
|
|
||||||
NoNewPrivileges = true;
|
|
||||||
ProtectHome = true;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
}
|
|
16
run-cmd.nix
16
run-cmd.nix
|
@ -1,16 +0,0 @@
|
||||||
{
|
|
||||||
stdenvNoCC,
|
|
||||||
src,
|
|
||||||
name,
|
|
||||||
cmd,
|
|
||||||
extraBuildInputs ? [ ],
|
|
||||||
extraNativeBuildInputs ? [ ],
|
|
||||||
}:
|
|
||||||
stdenvNoCC.mkDerivation {
|
|
||||||
name = "${name}-src";
|
|
||||||
inherit src;
|
|
||||||
buildInputs = extraBuildInputs;
|
|
||||||
nativeBuildInputs = extraNativeBuildInputs;
|
|
||||||
buildPhase = cmd;
|
|
||||||
installPhase = "mkdir $out";
|
|
||||||
}
|
|
Loading…
Reference in a new issue