aboutsummaryrefslogtreecommitdiff
path: root/nixpkgs/nixos/modules/services/network-filesystems/ipfs.nix
diff options
context:
space:
mode:
Diffstat (limited to 'nixpkgs/nixos/modules/services/network-filesystems/ipfs.nix')
-rw-r--r--nixpkgs/nixos/modules/services/network-filesystems/ipfs.nix189
1 files changed, 102 insertions, 87 deletions
diff --git a/nixpkgs/nixos/modules/services/network-filesystems/ipfs.nix b/nixpkgs/nixos/modules/services/network-filesystems/ipfs.nix
index 1f5c14d777d..f298f831fa7 100644
--- a/nixpkgs/nixos/modules/services/network-filesystems/ipfs.nix
+++ b/nixpkgs/nixos/modules/services/network-filesystems/ipfs.nix
@@ -1,69 +1,39 @@
-{ config, lib, pkgs, ... }:
+{ config, lib, pkgs, options, ... }:
with lib;
let
- inherit (pkgs) ipfs runCommand makeWrapper;
-
cfg = config.services.ipfs;
+ opt = options.services.ipfs;
ipfsFlags = toString ([
(optionalString cfg.autoMount "--mount")
- #(optionalString cfg.autoMigrate "--migrate")
(optionalString cfg.enableGC "--enable-gc")
(optionalString (cfg.serviceFdlimit != null) "--manage-fdlimit=false")
(optionalString (cfg.defaultMode == "offline") "--offline")
(optionalString (cfg.defaultMode == "norouting") "--routing=none")
] ++ cfg.extraFlags);
- defaultDataDir = if versionAtLeast config.system.stateVersion "17.09" then
- "/var/lib/ipfs" else
- "/var/lib/ipfs/.ipfs";
-
- # Wrapping the ipfs binary with the environment variable IPFS_PATH set to dataDir because we can't set it in the user environment
- wrapped = runCommand "ipfs" { buildInputs = [ makeWrapper ]; preferLocalBuild = true; } ''
- mkdir -p "$out/bin"
- makeWrapper "${ipfs}/bin/ipfs" "$out/bin/ipfs" \
- --set IPFS_PATH ${cfg.dataDir} \
- --prefix PATH : /run/wrappers/bin
- '';
+ splitMulitaddr = addrRaw: lib.tail (lib.splitString "/" addrRaw);
+
+ multiaddrToListenStream = addrRaw: let
+ addr = splitMulitaddr addrRaw;
+ s = builtins.elemAt addr;
+ in if s 0 == "ip4" && s 2 == "tcp"
+ then "${s 1}:${s 3}"
+ else if s 0 == "ip6" && s 2 == "tcp"
+ then "[${s 1}]:${s 3}"
+ else if s 0 == "unix"
+ then "/${lib.concatStringsSep "/" (lib.tail addr)}"
+ else null; # not valid for listen stream, skip
+
+ multiaddrToListenDatagram = addrRaw: let
+ addr = splitMulitaddr addrRaw;
+ s = builtins.elemAt addr;
+ in if s 0 == "ip4" && s 2 == "udp"
+ then "${s 1}:${s 3}"
+ else if s 0 == "ip6" && s 2 == "udp"
+ then "[${s 1}]:${s 3}"
+ else null; # not valid for listen datagram, skip
-
- commonEnv = {
- environment.IPFS_PATH = cfg.dataDir;
- path = [ wrapped ];
- serviceConfig.User = cfg.user;
- serviceConfig.Group = cfg.group;
- };
-
- baseService = recursiveUpdate commonEnv {
- wants = [ "ipfs-init.service" ];
- # NB: migration must be performed prior to pre-start, else we get the failure message!
- preStart = optionalString cfg.autoMount ''
- ipfs --local config Mounts.FuseAllowOther --json true
- ipfs --local config Mounts.IPFS ${cfg.ipfsMountDir}
- ipfs --local config Mounts.IPNS ${cfg.ipnsMountDir}
- '' + concatStringsSep "\n" (collect
- isString
- (mapAttrsRecursive
- (path: value:
- # Using heredoc below so that the value is never improperly quoted
- ''
- read value <<EOF
- ${builtins.toJSON value}
- EOF
- ipfs --local config --json "${concatStringsSep "." path}" "$value"
- '')
- ({ Addresses.API = cfg.apiAddress;
- Addresses.Gateway = cfg.gatewayAddress;
- Addresses.Swarm = cfg.swarmAddress;
- } //
- cfg.extraConfig))
- );
- serviceConfig = {
- ExecStart = "${wrapped}/bin/ipfs daemon ${ipfsFlags}";
- Restart = "on-failure";
- RestartSec = 1;
- } // optionalAttrs (cfg.serviceFdlimit != null) { LimitNOFILE = cfg.serviceFdlimit; };
- };
in {
###### interface
@@ -88,7 +58,9 @@ in {
dataDir = mkOption {
type = types.str;
- default = defaultDataDir;
+ default = if versionAtLeast config.system.stateVersion "17.09"
+ then "/var/lib/ipfs"
+ else "/var/lib/ipfs/.ipfs";
description = "The data dir for IPFS";
};
@@ -98,18 +70,6 @@ in {
description = "systemd service that is enabled by default";
};
- /*
- autoMigrate = mkOption {
- type = types.bool;
- default = false;
- description = ''
- Whether IPFS should try to migrate the file system automatically.
-
- The daemon will need to be able to download a binary from https://ipfs.io to perform the migration.
- '';
- };
- */
-
autoMount = mkOption {
type = types.bool;
default = false;
@@ -142,7 +102,12 @@ in {
swarmAddress = mkOption {
type = types.listOf types.str;
- default = [ "/ip4/0.0.0.0/tcp/4001" "/ip6/::/tcp/4001" ];
+ default = [
+ "/ip4/0.0.0.0/tcp/4001"
+ "/ip6/::/tcp/4001"
+ "/ip4/0.0.0.0/udp/4001/quic"
+ "/ip6/::/udp/4001/quic"
+ ];
description = "Where IPFS listens for incoming p2p connections";
};
@@ -199,13 +164,21 @@ in {
example = 64*1024;
};
+ startWhenNeeded = mkOption {
+ type = types.bool;
+ default = false;
+ description = "Whether to use socket activation to start IPFS when needed.";
+ };
+
};
};
###### implementation
config = mkIf cfg.enable {
- environment.systemPackages = [ wrapped ];
+ environment.systemPackages = [ pkgs.ipfs ];
+ environment.variables.IPFS_PATH = cfg.dataDir;
+
programs.fuse = mkIf cfg.autoMount {
userAllowOther = true;
};
@@ -234,10 +207,14 @@ in {
"d '${cfg.ipnsMountDir}' - ${cfg.user} ${cfg.group} - -"
];
- systemd.services.ipfs-init = recursiveUpdate commonEnv {
+ systemd.packages = [ pkgs.ipfs ];
+
+ systemd.services.ipfs-init = {
description = "IPFS Initializer";
- before = [ "ipfs.service" "ipfs-offline.service" "ipfs-norouting.service" ];
+ environment.IPFS_PATH = cfg.dataDir;
+
+ path = [ pkgs.ipfs ];
script = ''
if [[ ! -f ${cfg.dataDir}/config ]]; then
@@ -251,34 +228,72 @@ in {
fi
'';
+ wantedBy = [ "default.target" ];
+
serviceConfig = {
Type = "oneshot";
RemainAfterExit = true;
+ User = cfg.user;
+ Group = cfg.group;
};
};
- # TODO These 3 definitions possibly be further abstracted through use of a function
- # like: mutexServices "ipfs" [ "", "offline", "norouting" ] { ... shared conf here ... }
+ systemd.services.ipfs = {
+ path = [ "/run/wrappers" pkgs.ipfs ];
+ environment.IPFS_PATH = cfg.dataDir;
+
+ wants = [ "ipfs-init.service" ];
+ after = [ "ipfs-init.service" ];
- systemd.services.ipfs = recursiveUpdate baseService {
- description = "IPFS Daemon";
- wantedBy = mkIf (cfg.defaultMode == "online") [ "multi-user.target" ];
- after = [ "network.target" "ipfs-init.service" ];
- conflicts = [ "ipfs-offline.service" "ipfs-norouting.service"];
+ preStart = optionalString cfg.autoMount ''
+ ipfs --local config Mounts.FuseAllowOther --json true
+ ipfs --local config Mounts.IPFS ${cfg.ipfsMountDir}
+ ipfs --local config Mounts.IPNS ${cfg.ipnsMountDir}
+ '' + concatStringsSep "\n" (collect
+ isString
+ (mapAttrsRecursive
+ (path: value:
+ # Using heredoc below so that the value is never improperly quoted
+ ''
+ read value <<EOF
+ ${builtins.toJSON value}
+ EOF
+ ipfs --local config --json "${concatStringsSep "." path}" "$value"
+ '')
+ ({ Addresses.API = cfg.apiAddress;
+ Addresses.Gateway = cfg.gatewayAddress;
+ Addresses.Swarm = cfg.swarmAddress;
+ } //
+ cfg.extraConfig))
+ );
+ serviceConfig = {
+ ExecStart = ["" "${pkgs.ipfs}/bin/ipfs daemon ${ipfsFlags}"];
+ User = cfg.user;
+ Group = cfg.group;
+ } // optionalAttrs (cfg.serviceFdlimit != null) { LimitNOFILE = cfg.serviceFdlimit; };
+ } // optionalAttrs (!cfg.startWhenNeeded) {
+ wantedBy = [ "default.target" ];
};
- systemd.services.ipfs-offline = recursiveUpdate baseService {
- description = "IPFS Daemon (offline mode)";
- wantedBy = mkIf (cfg.defaultMode == "offline") [ "multi-user.target" ];
- after = [ "ipfs-init.service" ];
- conflicts = [ "ipfs.service" "ipfs-norouting.service"];
+ systemd.sockets.ipfs-gateway = {
+ wantedBy = [ "sockets.target" ];
+ socketConfig = {
+ ListenStream = let
+ fromCfg = multiaddrToListenStream cfg.gatewayAddress;
+ in [ "" ] ++ lib.optional (fromCfg != null) fromCfg;
+ ListenDatagram = let
+ fromCfg = multiaddrToListenDatagram cfg.gatewayAddress;
+ in [ "" ] ++ lib.optional (fromCfg != null) fromCfg;
+ };
};
- systemd.services.ipfs-norouting = recursiveUpdate baseService {
- description = "IPFS Daemon (no routing mode)";
- wantedBy = mkIf (cfg.defaultMode == "norouting") [ "multi-user.target" ];
- after = [ "ipfs-init.service" ];
- conflicts = [ "ipfs.service" "ipfs-offline.service"];
+ systemd.sockets.ipfs-api = {
+ wantedBy = [ "sockets.target" ];
+ # We also include "%t/ipfs.sock" because tere is no way to put the "%t"
+ # in the multiaddr.
+ socketConfig.ListenStream = let
+ fromCfg = multiaddrToListenStream cfg.apiAddress;
+ in [ "" "%t/ipfs.sock" ] ++ lib.optional (fromCfg != null) fromCfg;
};
};