Skip to content

Commit

Permalink
feat: add flag to disable containers tooling (#1367)
Browse files Browse the repository at this point in the history
  • Loading branch information
blackheaven committed Aug 10, 2024
1 parent 25e48e9 commit 14b40b5
Showing 1 changed file with 138 additions and 117 deletions.
255 changes: 138 additions & 117 deletions src/modules/containers.nix
Original file line number Diff line number Diff line change
Expand Up @@ -2,9 +2,11 @@

let
projectName = name:
if config.name == null
then throw ''You need to set `name = "myproject";` or `containers.${name}.name = "mycontainer"; to be able to generate a container.''
else config.name;
if config.name == null then
throw ''
You need to set `name = "myproject";` or `containers.${name}.name = "mycontainer"; to be able to generate a container.''
else
config.name;
types = lib.types;
envContainerName = builtins.getEnv "DEVENV_CONTAINER";

Expand All @@ -20,38 +22,43 @@ let
url = "github:rrbutani/nix-mk-shell-bin";
attribute = "containers";
};
shell = mk-shell-bin.lib.mkShellBin { drv = config.shell; nixpkgs = pkgs; };
shell = mk-shell-bin.lib.mkShellBin {
drv = config.shell;
nixpkgs = pkgs;
};
bash = "${pkgs.bashInteractive}/bin/bash";
mkEntrypoint = cfg: pkgs.writeScript "entrypoint" ''
#!${bash}
mkEntrypoint = cfg:
pkgs.writeScript "entrypoint" ''
#!${bash}
export PATH=/bin
export PATH=/bin
source ${shell.envScript}
source ${shell.envScript}
# expand any envvars before exec
cmd="`echo "$@"|${pkgs.envsubst}/bin/envsubst`"
# expand any envvars before exec
cmd="`echo "$@"|${pkgs.envsubst}/bin/envsubst`"
${bash} -c "$cmd"
'';
${bash} -c "$cmd"
'';
user = "user";
group = "user";
uid = "1000";
gid = "1000";
homeDir = "/env";

mkHome = path: (pkgs.runCommand "devenv-container-home" { } ''
mkdir -p $out${homeDir}
cp -R ${path}/* $out${homeDir}/
'');
mkHome = path:
(pkgs.runCommand "devenv-container-home" { } ''
mkdir -p $out${homeDir}
cp -R ${path}/* $out${homeDir}/
'');

mkMultiHome = paths: map mkHome paths;

homeRoots = cfg: (
if (builtins.typeOf cfg.copyToRoot == "list")
then cfg.copyToRoot
else [ cfg.copyToRoot ]
);
homeRoots = cfg:
(if (builtins.typeOf cfg.copyToRoot == "list") then
cfg.copyToRoot
else
[ cfg.copyToRoot ]);

mkTmp = (pkgs.runCommand "devenv-container-tmp" { } ''
mkdir -p $out/tmp
Expand Down Expand Up @@ -81,101 +88,102 @@ let
touch $out/etc/login.defs
'');

mkPerm = derivation:
{
path = derivation;
mode = "0744";
uid = lib.toInt uid;
gid = lib.toInt gid;
uname = user;
gname = group;
};

mkPerm = derivation: {
path = derivation;
mode = "0744";
uid = lib.toInt uid;
gid = lib.toInt gid;
uname = user;
gname = group;
};

mkDerivation = cfg: nix2container.nix2container.buildImage {
name = cfg.name;
tag = cfg.version;
initializeNixDatabase = true;
nixUid = lib.toInt uid;
nixGid = lib.toInt gid;

copyToRoot = [
(pkgs.buildEnv {
name = "devenv-container-root";
paths = [
pkgs.coreutils-full
pkgs.bashInteractive
pkgs.su
pkgs.sudo
];
pathsToLink = "/bin";
})
mkEtc
mkTmp
];

maxLayers = cfg.maxLayers;

layers = [
(nix2container.nix2container.buildLayer {
perms = map mkPerm (mkMultiHome (homeRoots cfg));
copyToRoot = mkMultiHome (homeRoots cfg);
})
];

perms = [
{
mkDerivation = cfg:
nix2container.nix2container.buildImage {
name = cfg.name;
tag = cfg.version;
initializeNixDatabase = cfg.isDev;
nixUid = lib.toInt uid;
nixGid = lib.toInt gid;

copyToRoot = lib.lists.optionals cfg.isDev [
(pkgs.buildEnv {
name = "devenv-container-root";
paths =
[ pkgs.coreutils-full pkgs.bashInteractive pkgs.su pkgs.sudo ];
pathsToLink = "/bin";
})
mkEtc
mkTmp
];

maxLayers = cfg.maxLayers;

layers = [
(nix2container.nix2container.buildLayer {
perms = map mkPerm (mkMultiHome (homeRoots cfg));
copyToRoot = mkMultiHome (homeRoots cfg);
})
];

perms = lib.lists.optionals cfg.isDev [{
path = mkTmp;
regex = "/tmp";
mode = "1777";
uid = 0;
gid = 0;
uname = "root";
gname = "root";
}
];

config = {
Entrypoint = cfg.entrypoint;
User = "${user}";
WorkingDir = "${homeDir}";
Env = lib.mapAttrsToList
(name: value:
"${name}=${toString value}"
)
config.env ++ [ "HOME=${homeDir}" "USER=${user}" ];
Cmd = [ cfg.startupCommand ];
}];

config = lib.attrsets.mergeAttrsList [
{
User = "${user}";
WorkingDir = "${homeDir}";
}
(if cfg.isDev then {
Env = lib.mapAttrsToList (name: value: "${name}=${toString value}")
config.env ++ [ "HOME=${homeDir}" "USER=${user}" ];
Entrypoint = cfg.entrypoint;
Cmd = [ cfg.startupCommand ];
} else
{ })
];
};
};

# <registry> <args>
mkCopyScript = cfg: pkgs.writeShellScript "copy-container" ''
set -e -o pipefail
container=$1
shift
if [[ "$1" == false ]]; then
registry=${cfg.registry}
else
registry="$1"
fi
shift
dest="''${registry}${cfg.name}:${cfg.version}"
if [[ $# == 0 ]]; then
args=(${if cfg.defaultCopyArgs == [] then "" else toString cfg.defaultCopyArgs})
else
args=("$@")
fi
echo
echo "Copying container $container to $dest"
echo
${nix2container.skopeo-nix2container}/bin/skopeo --insecure-policy copy "nix:$container" "$dest" ''${args[@]}
'';
mkCopyScript = cfg:
pkgs.writeShellScript "copy-container" ''
set -e -o pipefail
container=$1
shift
if [[ "$1" == false ]]; then
registry=${cfg.registry}
else
registry="$1"
fi
shift
dest="''${registry}${cfg.name}:${cfg.version}"
if [[ $# == 0 ]]; then
args=(${
if cfg.defaultCopyArgs == [ ] then
""
else
toString cfg.defaultCopyArgs
})
else
args=("$@")
fi
echo
echo "Copying container $container to $dest"
echo
${nix2container.skopeo-nix2container}/bin/skopeo --insecure-policy copy "nix:$container" "$dest" ''${args[@]}
'';
containerOptions = types.submodule ({ name, config, ... }: {
options = {
name = lib.mkOption {
Expand All @@ -193,7 +201,8 @@ let

copyToRoot = lib.mkOption {
type = types.either types.path (types.listOf types.path);
description = "Add a path to the container. Defaults to the whole git repo.";
description =
"Add a path to the container. Defaults to the whole git repo.";
default = self;
defaultText = "self";
};
Expand All @@ -213,11 +222,10 @@ let

defaultCopyArgs = lib.mkOption {
type = types.listOf types.str;
description =
''
Default arguments to pass to `skopeo copy`.
You can override them by passing arguments to the script.
'';
description = ''
Default arguments to pass to `skopeo copy`.
You can override them by passing arguments to the script.
'';
default = [ ];
};

Expand All @@ -236,7 +244,14 @@ let
isBuilding = lib.mkOption {
type = types.bool;
default = false;
description = "Set to true when the environment is building this container.";
description =
"Set to true when the environment is building this container.";
};

isDev = lib.mkOption {
type = types.bool;
default = true;
description = "Is a development containers (add tools).";
};

derivation = lib.mkOption {
Expand Down Expand Up @@ -266,14 +281,16 @@ in
containers = lib.mkOption {
type = types.attrsOf containerOptions;
default = { };
description = "Container specifications that can be built, copied and ran using `devenv container`.";
description =
"Container specifications that can be built, copied and ran using `devenv container`.";
};

container = {
isBuilding = lib.mkOption {
type = types.bool;
default = false;
description = "Set to true when the environment is building a container.";
description =
"Set to true when the environment is building a container.";
};
};
};
Expand All @@ -292,12 +309,16 @@ in
startupCommand = lib.mkDefault config.procfileScript;
};
}
(if envContainerName == "" then { } else {
(if envContainerName == "" then
{ }
else {
containers.${envContainerName}.isBuilding = true;
})
(lib.mkIf config.container.isBuilding {
devenv.tmpdir = lib.mkOverride (lib.modules.defaultOverridePriority - 1) "/tmp";
devenv.runtime = lib.mkOverride (lib.modules.defaultOverridePriority - 1) "${config.devenv.tmpdir}/devenv";
devenv.tmpdir =
lib.mkOverride (lib.modules.defaultOverridePriority - 1) "/tmp";
devenv.runtime = lib.mkOverride (lib.modules.defaultOverridePriority - 1)
"${config.devenv.tmpdir}/devenv";
devenv.root = lib.mkForce "${homeDir}";
devenv.dotfile = lib.mkOverride 49 "${homeDir}/.devenv";
})
Expand Down

0 comments on commit 14b40b5

Please sign in to comment.