@@ -74,6 +74,52 @@ in
|
||||
See: https://man7.org/linux/man-pages/man7/vsock.7.html
|
||||
'';
|
||||
};
|
||||
|
||||
extraMounts = mkOption {
|
||||
type = types.attrsOf (types.submodule {
|
||||
options = {
|
||||
hostPath = mkOption {
|
||||
type = types.str;
|
||||
description = "Path on the host to bind-mount into the workspace.";
|
||||
};
|
||||
containerPath = mkOption {
|
||||
type = types.str;
|
||||
description = "Mount point inside the workspace.";
|
||||
};
|
||||
createHostPath = mkOption {
|
||||
type = types.bool;
|
||||
default = true;
|
||||
description = ''
|
||||
Whether the workspace setup service should `mkdir -p` the
|
||||
hostPath before the workspace starts. Set to false when the
|
||||
source is managed by another service (e.g. an agenix secret
|
||||
file at /run/agenix/<name>) so the setup doesn't race or
|
||||
collide with the producing service.
|
||||
'';
|
||||
};
|
||||
shift = mkOption {
|
||||
type = types.bool;
|
||||
default = true;
|
||||
description = ''
|
||||
Pass `shift=true` to the Incus disk device so host UIDs/GIDs
|
||||
are remapped into the container's userns. Set to false when
|
||||
the source filesystem can't be idmapped (e.g. tmpfs under
|
||||
/run on kernels without tmpfs-idmap support). With shift
|
||||
disabled, host-owned files show up as nobody:nogroup inside
|
||||
the container — make the file world-readable (mode 0444) if
|
||||
you need processes inside to read it.
|
||||
'';
|
||||
};
|
||||
};
|
||||
});
|
||||
default = { };
|
||||
description = ''
|
||||
Additional host→workspace bind mounts beyond the default workspace/,
|
||||
ssh-host-keys/, and claude-config/ mounts. Useful for persisting state
|
||||
(e.g. /var/lib/hermes) across container recreations on nixos-rebuild.
|
||||
Only honored by the "incus" backend currently.
|
||||
'';
|
||||
};
|
||||
};
|
||||
});
|
||||
default = { };
|
||||
@@ -82,6 +128,13 @@ in
|
||||
};
|
||||
|
||||
config = mkIf cfg.enable {
|
||||
assertions = lib.mapAttrsToList
|
||||
(name: ws: {
|
||||
assertion = ws.extraMounts == { } || ws.type == "incus";
|
||||
message = ''sandboxed-workspace.workspaces.${name}: extraMounts is only supported for type = "incus" (got "${ws.type}").'';
|
||||
})
|
||||
cfg.workspaces;
|
||||
|
||||
# Automatically enable sandbox networking when workspaces are defined
|
||||
networking.sandbox.enable = mkIf (cfg.workspaces != { }) true;
|
||||
|
||||
@@ -145,7 +198,7 @@ in
|
||||
mkdir -p /home/googlebot/sandboxed/${name}/workspace
|
||||
mkdir -p /home/googlebot/sandboxed/${name}/ssh-host-keys
|
||||
mkdir -p /home/googlebot/sandboxed/${name}/claude-config
|
||||
|
||||
${lib.concatMapStrings (m: "mkdir -p ${m.hostPath}\n ") (lib.filter (m: m.createHostPath) (lib.attrValues ws.extraMounts))}
|
||||
# Fix ownership
|
||||
chown -R googlebot:users /home/googlebot/sandboxed/${name}
|
||||
|
||||
|
||||
@@ -16,6 +16,14 @@
|
||||
programs.starship.enableFishIntegration = true;
|
||||
programs.starship.settings.container.disabled = true;
|
||||
|
||||
# Land in ~/workspace on interactive login. Skipped if the dir doesn't exist
|
||||
# (e.g. before the bind mount is wired) so we don't error on shell startup.
|
||||
programs.fish.loginShellInit = ''
|
||||
if test -d $HOME/workspace
|
||||
cd $HOME/workspace
|
||||
end
|
||||
'';
|
||||
|
||||
# Basic command-line tools
|
||||
programs.btop.enable = true;
|
||||
programs.ripgrep.enable = true;
|
||||
|
||||
@@ -16,6 +16,7 @@ let
|
||||
let
|
||||
nixpkgs = hostConfig.inputs.nixpkgs;
|
||||
containerSystem = nixpkgs.lib.nixosSystem {
|
||||
specialArgs = { inherit hostConfig; };
|
||||
modules = [
|
||||
(import ./base.nix {
|
||||
inherit hostConfig;
|
||||
@@ -65,6 +66,9 @@ let
|
||||
incus config device add ${containerName} workspace disk source=/home/googlebot/sandboxed/${name}/workspace path=/home/googlebot/workspace shift=true
|
||||
incus config device add ${containerName} ssh-keys disk source=/home/googlebot/sandboxed/${name}/ssh-host-keys path=/etc/ssh-host-keys shift=true
|
||||
incus config device add ${containerName} claude-config disk source=/home/googlebot/sandboxed/${name}/claude-config path=/home/googlebot/claude-config shift=true
|
||||
${lib.concatStrings (lib.mapAttrsToList (mountName: m: ''
|
||||
incus config device add ${containerName} ${mountName} disk source=${m.hostPath} path=${m.containerPath} shift=${lib.boolToString m.shift}
|
||||
'') ws.extraMounts)}
|
||||
'';
|
||||
in
|
||||
{
|
||||
|
||||
Reference in New Issue
Block a user