mirror of
https://github.com/NixOS/nixpkgs.git
synced 2025-06-13 05:05:29 +03:00
nixos/switch-to-configuration: Add dry activation scripts
This commit is contained in:
parent
5942b67b0c
commit
3156730402
3 changed files with 71 additions and 42 deletions
|
@ -17,6 +17,41 @@ let
|
||||||
'';
|
'';
|
||||||
});
|
});
|
||||||
|
|
||||||
|
systemActivationScript = set: onlyDry: let
|
||||||
|
set' = filterAttrs (_: v: onlyDry -> v.supportsDryActivation) (mapAttrs (_: v: if isString v then (noDepEntry v) // { supportsDryActivation = false; } else v) set);
|
||||||
|
withHeadlines = addAttributeName set';
|
||||||
|
in
|
||||||
|
''
|
||||||
|
#!${pkgs.runtimeShell}
|
||||||
|
|
||||||
|
systemConfig='@out@'
|
||||||
|
|
||||||
|
export PATH=/empty
|
||||||
|
for i in ${toString path}; do
|
||||||
|
PATH=$PATH:$i/bin:$i/sbin
|
||||||
|
done
|
||||||
|
|
||||||
|
_status=0
|
||||||
|
trap "_status=1 _localstatus=\$?" ERR
|
||||||
|
|
||||||
|
# Ensure a consistent umask.
|
||||||
|
umask 0022
|
||||||
|
|
||||||
|
${textClosureMap id (withHeadlines) (attrNames withHeadlines)}
|
||||||
|
|
||||||
|
'' + optionalString (!onlyDry) ''
|
||||||
|
# Make this configuration the current configuration.
|
||||||
|
# The readlink is there to ensure that when $systemConfig = /system
|
||||||
|
# (which is a symlink to the store), /run/current-system is still
|
||||||
|
# used as a garbage collection root.
|
||||||
|
ln -sfn "$(readlink -f "$systemConfig")" /run/current-system
|
||||||
|
|
||||||
|
# Prevent the current configuration from being garbage-collected.
|
||||||
|
ln -sfn /run/current-system /nix/var/nix/gcroots/current-system
|
||||||
|
|
||||||
|
exit $_status
|
||||||
|
'';
|
||||||
|
|
||||||
path = with pkgs; map getBin
|
path = with pkgs; map getBin
|
||||||
[ coreutils
|
[ coreutils
|
||||||
gnugrep
|
gnugrep
|
||||||
|
@ -28,7 +63,7 @@ let
|
||||||
util-linux # needed for mount and mountpoint
|
util-linux # needed for mount and mountpoint
|
||||||
];
|
];
|
||||||
|
|
||||||
scriptType = with types;
|
scriptType = withDry: with types;
|
||||||
let scriptOptions =
|
let scriptOptions =
|
||||||
{ deps = mkOption
|
{ deps = mkOption
|
||||||
{ type = types.listOf types.str;
|
{ type = types.listOf types.str;
|
||||||
|
@ -39,6 +74,19 @@ let
|
||||||
{ type = types.lines;
|
{ type = types.lines;
|
||||||
description = "The content of the script.";
|
description = "The content of the script.";
|
||||||
};
|
};
|
||||||
|
} // optionalAttrs withDry {
|
||||||
|
supportsDryActivation = mkOption
|
||||||
|
{ type = types.bool;
|
||||||
|
default = false;
|
||||||
|
description = ''
|
||||||
|
Whether this activation script supports being dry-activated.
|
||||||
|
These activation scripts will also be executed on dry-activate
|
||||||
|
activations with the environment variable
|
||||||
|
<literal>NIXOS_ACTION</literal> being set to <literal>dry-activate
|
||||||
|
</literal>. it's important that these activation scripts don't
|
||||||
|
modify anything about the system when the variable is set.
|
||||||
|
'';
|
||||||
|
};
|
||||||
};
|
};
|
||||||
in either str (submodule { options = scriptOptions; });
|
in either str (submodule { options = scriptOptions; });
|
||||||
|
|
||||||
|
@ -74,47 +122,19 @@ in
|
||||||
idempotent and fast.
|
idempotent and fast.
|
||||||
'';
|
'';
|
||||||
|
|
||||||
type = types.attrsOf scriptType;
|
type = types.attrsOf (scriptType true);
|
||||||
|
apply = set: set // {
|
||||||
apply = set: {
|
script = systemActivationScript set false;
|
||||||
script =
|
|
||||||
''
|
|
||||||
#! ${pkgs.runtimeShell}
|
|
||||||
|
|
||||||
systemConfig=@out@
|
|
||||||
|
|
||||||
export PATH=/empty
|
|
||||||
for i in ${toString path}; do
|
|
||||||
PATH=$PATH:$i/bin:$i/sbin
|
|
||||||
done
|
|
||||||
|
|
||||||
_status=0
|
|
||||||
trap "_status=1 _localstatus=\$?" ERR
|
|
||||||
|
|
||||||
# Ensure a consistent umask.
|
|
||||||
umask 0022
|
|
||||||
|
|
||||||
${
|
|
||||||
let
|
|
||||||
set' = mapAttrs (n: v: if isString v then noDepEntry v else v) set;
|
|
||||||
withHeadlines = addAttributeName set';
|
|
||||||
in textClosureMap id (withHeadlines) (attrNames withHeadlines)
|
|
||||||
}
|
|
||||||
|
|
||||||
# Make this configuration the current configuration.
|
|
||||||
# The readlink is there to ensure that when $systemConfig = /system
|
|
||||||
# (which is a symlink to the store), /run/current-system is still
|
|
||||||
# used as a garbage collection root.
|
|
||||||
ln -sfn "$(readlink -f "$systemConfig")" /run/current-system
|
|
||||||
|
|
||||||
# Prevent the current configuration from being garbage-collected.
|
|
||||||
ln -sfn /run/current-system /nix/var/nix/gcroots/current-system
|
|
||||||
|
|
||||||
exit $_status
|
|
||||||
'';
|
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
|
|
||||||
|
system.dryActivationScript = mkOption {
|
||||||
|
description = "The shell script that is to be run when dry-activating a system.";
|
||||||
|
readOnly = true;
|
||||||
|
internal = true;
|
||||||
|
default = systemActivationScript (removeAttrs config.system.activationScripts [ "script" ]) true;
|
||||||
|
};
|
||||||
|
|
||||||
system.userActivationScripts = mkOption {
|
system.userActivationScripts = mkOption {
|
||||||
default = {};
|
default = {};
|
||||||
|
|
||||||
|
@ -137,7 +157,7 @@ in
|
||||||
idempotent and fast.
|
idempotent and fast.
|
||||||
'';
|
'';
|
||||||
|
|
||||||
type = with types; attrsOf scriptType;
|
type = with types; attrsOf (scriptType false);
|
||||||
|
|
||||||
apply = set: {
|
apply = set: {
|
||||||
script = ''
|
script = ''
|
||||||
|
|
|
@ -36,6 +36,8 @@ EOF
|
||||||
exit 1;
|
exit 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
$ENV{NIXOS_ACTION} = $action;
|
||||||
|
|
||||||
# This is a NixOS installation if it has /etc/NIXOS or a proper
|
# This is a NixOS installation if it has /etc/NIXOS or a proper
|
||||||
# /etc/os-release.
|
# /etc/os-release.
|
||||||
die "This is not a NixOS installation!\n" unless
|
die "This is not a NixOS installation!\n" unless
|
||||||
|
@ -360,6 +362,10 @@ if ($action eq "dry-activate") {
|
||||||
if scalar @unitsToStopFiltered > 0;
|
if scalar @unitsToStopFiltered > 0;
|
||||||
print STDERR "would NOT stop the following changed units: ", join(", ", sort(keys %unitsToSkip)), "\n"
|
print STDERR "would NOT stop the following changed units: ", join(", ", sort(keys %unitsToSkip)), "\n"
|
||||||
if scalar(keys %unitsToSkip) > 0;
|
if scalar(keys %unitsToSkip) > 0;
|
||||||
|
|
||||||
|
print STDERR "would activate the configuration...\n";
|
||||||
|
system("$out/dry-activate", "$out");
|
||||||
|
|
||||||
print STDERR "would restart systemd\n" if $restartSystemd;
|
print STDERR "would restart systemd\n" if $restartSystemd;
|
||||||
print STDERR "would restart the following units: ", join(", ", sort(keys %unitsToRestart)), "\n"
|
print STDERR "would restart the following units: ", join(", ", sort(keys %unitsToRestart)), "\n"
|
||||||
if scalar(keys %unitsToRestart) > 0;
|
if scalar(keys %unitsToRestart) > 0;
|
||||||
|
|
|
@ -56,9 +56,11 @@ let
|
||||||
''}
|
''}
|
||||||
|
|
||||||
echo "$activationScript" > $out/activate
|
echo "$activationScript" > $out/activate
|
||||||
|
echo "$dryActivationScript" > $out/dry-activate
|
||||||
substituteInPlace $out/activate --subst-var out
|
substituteInPlace $out/activate --subst-var out
|
||||||
chmod u+x $out/activate
|
substituteInPlace $out/dry-activate --subst-var out
|
||||||
unset activationScript
|
chmod u+x $out/activate $out/dry-activate
|
||||||
|
unset activationScript dryActivationScript
|
||||||
|
|
||||||
cp ${config.system.build.bootStage2} $out/init
|
cp ${config.system.build.bootStage2} $out/init
|
||||||
substituteInPlace $out/init --subst-var-by systemConfig $out
|
substituteInPlace $out/init --subst-var-by systemConfig $out
|
||||||
|
@ -108,6 +110,7 @@ let
|
||||||
config.system.build.installBootLoader
|
config.system.build.installBootLoader
|
||||||
or "echo 'Warning: do not know how to make this configuration bootable; please enable a boot loader.' 1>&2; true";
|
or "echo 'Warning: do not know how to make this configuration bootable; please enable a boot loader.' 1>&2; true";
|
||||||
activationScript = config.system.activationScripts.script;
|
activationScript = config.system.activationScripts.script;
|
||||||
|
dryActivationScript = config.system.dryActivationScript;
|
||||||
nixosLabel = config.system.nixos.label;
|
nixosLabel = config.system.nixos.label;
|
||||||
|
|
||||||
configurationName = config.boot.loader.grub.configurationName;
|
configurationName = config.boot.loader.grub.configurationName;
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue