home-manager: move profile management

This commit separates profile management (setting profile and creating
GC root) from file management (removing and adding managed files
within the user's home directory).

This is a step towards deprecating profile management within the
activation script, instead relying on the caller of the activation
script managing the profile.
This commit is contained in:
Robert Helgesson 2024-12-28 23:46:50 +01:00
parent 1e2a9d2d29
commit 1e68dc759b
Failed to generate hash of commit
6 changed files with 92 additions and 133 deletions

View file

@ -8,7 +8,7 @@ msgid ""
msgstr ""
"Project-Id-Version: Home Manager\n"
"Report-Msgid-Bugs-To: https://github.com/nix-community/home-manager/issues\n"
"POT-Creation-Date: 2024-04-17 23:19+0200\n"
"POT-Creation-Date: 2025-01-03 09:09+0100\n"
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
"Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
"Language-Team: LANGUAGE <LL@li.org>\n"
@ -23,36 +23,36 @@ msgstr ""
msgid "%s: missing argument for %s"
msgstr ""
#: home-manager/home-manager:64
#: home-manager/home-manager:69
msgid "No configuration file found at %s"
msgstr ""
#. translators: The first '%s' specifier will be replaced by either
#. 'home.nix' or 'flake.nix'.
#: home-manager/home-manager:81 home-manager/home-manager:85
#: home-manager/home-manager:184
#: home-manager/home-manager:86 home-manager/home-manager:90
#: home-manager/home-manager:189
msgid ""
"Keeping your Home Manager %s in %s is deprecated,\n"
"please move it to %s"
msgstr ""
#: home-manager/home-manager:92
#: home-manager/home-manager:97
msgid "No configuration file found. Please create one at %s"
msgstr ""
#: home-manager/home-manager:107
#: home-manager/home-manager:112
msgid "Home Manager not found at %s."
msgstr ""
#. translators: This message will be seen by very few users that likely are familiar with English. So feel free to leave this untranslated.
#: home-manager/home-manager:115
#: home-manager/home-manager:120
msgid ""
"The fallback Home Manager path %s has been deprecated and a file/directory "
"was found there."
msgstr ""
#. translators: This message will be seen by very few users that likely are familiar with English. So feel free to leave this untranslated.
#: home-manager/home-manager:118
#: home-manager/home-manager:123
msgid ""
"To remove this warning, do one of the following.\n"
"\n"
@ -73,42 +73,42 @@ msgid ""
" $ rm -r \"%s\""
msgstr ""
#: home-manager/home-manager:146
#: home-manager/home-manager:151
msgid "Sanity checking Nix"
msgstr ""
#: home-manager/home-manager:166
#: home-manager/home-manager:171
msgid "Could not find suitable profile directory, tried %s and %s"
msgstr ""
#. translators: Here "flake" is a noun that refers to the Nix Flakes feature.
#: home-manager/home-manager:221
#: home-manager/home-manager:226
msgid "Can't inspect options of a flake configuration"
msgstr ""
#: home-manager/home-manager:296 home-manager/home-manager:319
#: home-manager/home-manager:1051
#: home-manager/home-manager:301 home-manager/home-manager:324
#: home-manager/home-manager:1061
msgid "%s: unknown option '%s'"
msgstr ""
#: home-manager/home-manager:301 home-manager/home-manager:1052
#: home-manager/home-manager:306 home-manager/home-manager:1062
msgid "Run '%s --help' for usage help"
msgstr ""
#: home-manager/home-manager:327 home-manager/home-manager:431
#: home-manager/home-manager:332 home-manager/home-manager:437
msgid "The file %s already exists, leaving it unchanged..."
msgstr ""
#: home-manager/home-manager:329 home-manager/home-manager:433
#: home-manager/home-manager:334 home-manager/home-manager:439
msgid "Creating %s..."
msgstr ""
#: home-manager/home-manager:475
#: home-manager/home-manager:481
msgid "Creating initial Home Manager generation..."
msgstr ""
#. translators: The "%s" specifier will be replaced by a file path.
#: home-manager/home-manager:480
#: home-manager/home-manager:486
msgid ""
"All done! The home-manager tool should now be installed and you can edit\n"
"\n"
@ -119,7 +119,7 @@ msgid ""
msgstr ""
#. translators: The "%s" specifier will be replaced by a URL.
#: home-manager/home-manager:485
#: home-manager/home-manager:491
msgid ""
"Uh oh, the installation failed! Please create an issue at\n"
"\n"
@ -129,11 +129,11 @@ msgid ""
msgstr ""
#. translators: Here "flake" is a noun that refers to the Nix Flakes feature.
#: home-manager/home-manager:496
#: home-manager/home-manager:502
msgid "Can't instantiate a flake configuration"
msgstr ""
#: home-manager/home-manager:572
#: home-manager/home-manager:578
msgid ""
"There is %d unread and relevant news item.\n"
"Read it by running the command \"%s news\"."
@ -143,72 +143,72 @@ msgid_plural ""
msgstr[0] ""
msgstr[1] ""
#: home-manager/home-manager:586
#: home-manager/home-manager:592
msgid "Unknown \"news.display\" setting \"%s\"."
msgstr ""
#: home-manager/home-manager:594
#: home-manager/home-manager:600
#, sh-format
msgid "Please set the $EDITOR or $VISUAL environment variable"
msgstr ""
#: home-manager/home-manager:612
#: home-manager/home-manager:618
msgid "Cannot run build in read-only directory"
msgstr ""
#: home-manager/home-manager:693
#: home-manager/home-manager:699
msgid "No generation with ID %s"
msgstr ""
#: home-manager/home-manager:695
#: home-manager/home-manager:701
msgid "Cannot remove the current generation %s"
msgstr ""
#: home-manager/home-manager:697
#: home-manager/home-manager:703
msgid "Removing generation %s"
msgstr ""
#: home-manager/home-manager:718
#: home-manager/home-manager:724
msgid "No generations to expire"
msgstr ""
#: home-manager/home-manager:729
#: home-manager/home-manager:735
msgid "No home-manager packages seem to be installed."
msgstr ""
#: home-manager/home-manager:811
#: home-manager/home-manager:820
msgid "Unknown argument %s"
msgstr ""
#: home-manager/home-manager:835
#: home-manager/home-manager:845
msgid "This will remove Home Manager from your system."
msgstr ""
#: home-manager/home-manager:838
#: home-manager/home-manager:848
msgid "This is a dry run, nothing will actually be uninstalled."
msgstr ""
#: home-manager/home-manager:842
#: home-manager/home-manager:852
msgid "Really uninstall Home Manager?"
msgstr ""
#: home-manager/home-manager:848
#: home-manager/home-manager:858
msgid "Switching to empty Home Manager configuration..."
msgstr ""
#: home-manager/home-manager:863
#: home-manager/home-manager:873
msgid "Yay!"
msgstr ""
#: home-manager/home-manager:868
#: home-manager/home-manager:878
msgid "Home Manager is uninstalled but your home.nix is left untouched."
msgstr ""
#: home-manager/home-manager:1091
#: home-manager/home-manager:1101
msgid "expire-generations expects one argument, got %d."
msgstr ""
#: home-manager/home-manager:1113
#: home-manager/home-manager:1123
msgid "Unknown command: %s"
msgstr ""

View file

@ -105,10 +105,7 @@ in
# 1. Remove files from the old generation that are not in the new
# generation.
#
# 2. Switch over the Home Manager gcroot and current profile
# links.
#
# 3. Symlink files from the new generation into $HOME.
# 2. Symlink files from the new generation into $HOME.
#
# This order is needed to ensure that we always know which links
# belong to which generation. Specifically, if we're moving from
@ -215,28 +212,6 @@ in
}
cleanOldGen
if [[ ! -v oldGenPath || "$oldGenPath" != "$newGenPath" ]] ; then
_i "Creating profile generation %s" $newGenNum
if [[ -e "$genProfilePath"/manifest.json ]] ; then
# Remove all packages from "$genProfilePath"
# `nix profile remove '.*' --profile "$genProfilePath"` was not working, so here is a workaround:
nix profile list --profile "$genProfilePath" \
| cut -d ' ' -f 4 \
| xargs -rt $DRY_RUN_CMD nix profile remove $VERBOSE_ARG --profile "$genProfilePath"
run nix profile install $VERBOSE_ARG --profile "$genProfilePath" "$newGenPath"
else
run nix-env $VERBOSE_ARG --profile "$genProfilePath" --set "$newGenPath"
fi
run --quiet nix-store --realise "$newGenPath" --add-root "$newGenGcPath" --indirect
if [[ -e "$legacyGenGcPath" ]]; then
run rm $VERBOSE_ARG "$legacyGenGcPath"
fi
else
_i "No change so reusing latest profile generation %s" "$oldGenNum"
fi
linkNewGen
''
);

View file

@ -583,9 +583,17 @@ in
home.packages = [ config.home.sessionVariablesPackage ];
# A dummy entry acting as a boundary between the activation
# script's "check" and the "write" phases.
home.activation.writeBoundary = hm.dag.entryAnywhere "";
# The entry acting as a boundary between the activation script's "check" and
# the "write" phases. This is where we commit to attempting to actually
# activate the configuration.
home.activation.writeBoundary = hm.dag.entryAnywhere ''
if [[ ! -v oldGenPath || "$oldGenPath" != "$newGenPath" ]] ; then
_i "Creating new profile generation"
run nix-env $VERBOSE_ARG --profile "$genProfilePath" --set "$newGenPath"
else
_i "No change so reusing latest profile generation"
fi
'';
# Install packages to the user environment.
#
@ -718,7 +726,20 @@ in
checkHomeDirectory ${escapeShellArg config.home.homeDirectory}
fi
# Create a temporary GC root to prevent collection during activation.
trap 'run rm -f $VERBOSE_ARG "$newGenGcPath"' EXIT
run --silence nix-store --realise "$newGenPath" --add-root "$newGenGcPath"
${activationCmds}
${optionalString (!config.uninstall) ''
# Create the "current generation" GC root.
run --silence nix-store --realise "$newGenPath" --add-root "$currentGenGcPath"
if [[ -e "$legacyGenGcPath" ]]; then
run rm $VERBOSE_ARG "$legacyGenGcPath"
fi
''}
'';
in
pkgs.runCommand

View file

@ -59,34 +59,13 @@ function setupVars() {
declare -gr hmDataPath="${XDG_DATA_HOME:-$HOME/.local/share}/home-manager"
declare -gr genProfilePath="$profilesDir/home-manager"
declare -gr newGenPath="@GENERATION_DIR@";
declare -gr newGenGcPath="$hmGcrootsDir/current-home"
declare -gr newGenGcPath="$hmGcrootsDir/new-home"
declare -gr currentGenGcPath="$hmGcrootsDir/current-home"
declare -gr legacyGenGcPath="$globalGcrootsDir/current-home"
declare greatestGenNum
greatestGenNum=$( \
nix-env --list-generations --profile "$genProfilePath" \
| tail -1 \
| sed -E 's/ *([[:digit:]]+) .*/\1/')
if [[ -n $greatestGenNum ]] ; then
declare -gr oldGenNum=$greatestGenNum
declare -gr newGenNum=$((oldGenNum + 1))
else
declare -gr newGenNum=1
fi
if [[ -e $genProfilePath ]] ; then
if [[ -e $currentGenGcPath ]] ; then
declare -g oldGenPath
oldGenPath="$(readlink -e "$genProfilePath")"
fi
_iVerbose "Sanity checking oldGenNum and oldGenPath"
if [[ -v oldGenNum && ! -v oldGenPath
|| ! -v oldGenNum && -v oldGenPath ]]; then
_i $'The previous generation number and path are in conflict! These\nmust be either both empty or both set but are now set to\n\n \'%s\' and \'%s\'\n\nIf you don\'t mind losing previous profile generations then\nthe easiest solution is probably to run\n\n rm %s/home-manager*\n rm %s/current-home\n\nand trying home-manager switch again. Good luck!' \
"${oldGenNum:-}" "${oldGenPath:-}" \
"$profilesDir" "$hmGcrootsDir"
exit 1
oldGenPath="$(readlink -e "$currentGenGcPath")"
fi
}
@ -181,15 +160,13 @@ if [[ -v VERBOSE ]]; then
fi
_iVerbose "Activation variables:"
if [[ -v oldGenNum ]] ; then
verboseEcho " oldGenNum=$oldGenNum"
if [[ -v oldGenPath ]] ; then
verboseEcho " oldGenPath=$oldGenPath"
else
verboseEcho " oldGenNum undefined (first run?)"
verboseEcho " oldGenPath undefined (first run?)"
fi
verboseEcho " newGenPath=$newGenPath"
verboseEcho " newGenNum=$newGenNum"
verboseEcho " genProfilePath=$genProfilePath"
verboseEcho " newGenGcPath=$newGenGcPath"
verboseEcho " currentGenGcPath=$currentGenGcPath"
verboseEcho " legacyGenGcPath=$legacyGenGcPath"

View file

@ -8,7 +8,7 @@ msgid ""
msgstr ""
"Project-Id-Version: Home Manager Modules\n"
"Report-Msgid-Bugs-To: https://github.com/nix-community/home-manager/issues\n"
"POT-Creation-Date: 2024-04-17 23:19+0200\n"
"POT-Creation-Date: 2025-01-03 09:09+0100\n"
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
"Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
"Language-Team: LANGUAGE <LL@li.org>\n"
@ -17,23 +17,23 @@ msgstr ""
"Content-Type: text/plain; charset=CHARSET\n"
"Content-Transfer-Encoding: 8bit\n"
#: modules/files.nix:191
#: modules/files.nix:188
msgid "Creating home file links in %s"
msgstr ""
#: modules/files.nix:204
#: modules/files.nix:201
msgid "Cleaning up orphan links from %s"
msgstr ""
#: modules/files.nix:220
msgid "Creating profile generation %s"
#: modules/home-environment.nix:591
msgid "Creating new profile generation"
msgstr ""
#: modules/files.nix:237
msgid "No change so reusing latest profile generation %s"
#: modules/home-environment.nix:594
msgid "No change so reusing latest profile generation"
msgstr ""
#: modules/home-environment.nix:634
#: modules/home-environment.nix:643
msgid ""
"Oops, Nix failed to install your new Home Manager profile!\n"
"\n"
@ -49,7 +49,7 @@ msgid ""
"Then try activating your Home Manager configuration again."
msgstr ""
#: modules/home-environment.nix:667
#: modules/home-environment.nix:676
msgid "Activating %s"
msgstr ""
@ -61,54 +61,34 @@ msgstr ""
msgid "Could not find suitable profile directory, tried %s and %s"
msgstr ""
#: modules/lib-bash/activation-init.sh:83
msgid "Sanity checking oldGenNum and oldGenPath"
msgstr ""
#: modules/lib-bash/activation-init.sh:86
msgid ""
"The previous generation number and path are in conflict! These\n"
"must be either both empty or both set but are now set to\n"
"\n"
" '%s' and '%s'\n"
"\n"
"If you don't mind losing previous profile generations then\n"
"the easiest solution is probably to run\n"
"\n"
" rm %s/home-manager*\n"
" rm %s/current-home\n"
"\n"
"and trying home-manager switch again. Good luck!"
msgstr ""
#: modules/lib-bash/activation-init.sh:127
#: modules/lib-bash/activation-init.sh:106
msgid "Error: USER is set to \"%s\" but we expect \"%s\""
msgstr ""
#: modules/lib-bash/activation-init.sh:136
#: modules/lib-bash/activation-init.sh:115
msgid "Error: HOME is set to \"%s\" but we expect \"%s\""
msgstr ""
#: modules/lib-bash/activation-init.sh:153
#: modules/lib-bash/activation-init.sh:132
msgid "Starting Home Manager activation"
msgstr ""
#: modules/lib-bash/activation-init.sh:157
#: modules/lib-bash/activation-init.sh:136
msgid "Sanity checking Nix"
msgstr ""
#: modules/lib-bash/activation-init.sh:170
#: modules/lib-bash/activation-init.sh:149
msgid "This is a dry run"
msgstr ""
#: modules/lib-bash/activation-init.sh:174
#: modules/lib-bash/activation-init.sh:153
msgid "This is a live run"
msgstr ""
#: modules/lib-bash/activation-init.sh:180
#: modules/lib-bash/activation-init.sh:159
msgid "Using Nix version: %s"
msgstr ""
#: modules/lib-bash/activation-init.sh:183
#: modules/lib-bash/activation-init.sh:162
msgid "Activation variables:"
msgstr ""

View file

@ -49,6 +49,12 @@
# Create a persistent login so that Alice has a systemd session.
login_as_alice()
# Make sure that Alice has a "nix profile" compatible profile.
if True:
succeed_as_alice("nix profile install nixpkgs#cowsay")
result = succeed_as_alice("cowsay Hello")
machine.log(f"\n{result}")
with subtest("Home Manager installation"):
succeed_as_alice("nix run home-manager -- init --home-manager-url home-manager --nixpkgs-url nixpkgs --switch")