about summary refs log tree commit diff
diff options
context:
space:
mode:
authorEelco Dolstra <edolstra@gmail.com>2019-10-09T17·21+0200
committerEelco Dolstra <edolstra@gmail.com>2019-10-09T22·00+0200
commitf66108f738b43bf822b06d7ab62c0b7129fb454c (patch)
treef91a15c48c82d146e36de0b1fc727de44b5dc837
parent2070d55b0b3c39cc2e8b7ce3eb13567c92bd5433 (diff)
nix-env: Create ~/.nix-profile automatically
(cherry picked from commit 9348f9291e5d9e4ba3c4347ea1b235640f54fd79)
-rw-r--r--scripts/nix-profile-daemon.sh.in9
-rw-r--r--scripts/nix-profile.sh.in12
-rw-r--r--src/libstore/local-store.cc15
-rw-r--r--src/libutil/util.cc10
-rw-r--r--src/libutil/util.hh2
-rwxr-xr-xsrc/nix-channel/nix-channel.cc8
-rw-r--r--src/nix-env/nix-env.cc11
-rw-r--r--tests/nix-channel.sh4
-rw-r--r--tests/nix-profile.sh2
9 files changed, 31 insertions, 42 deletions
diff --git a/scripts/nix-profile-daemon.sh.in b/scripts/nix-profile-daemon.sh.in
index 2133a6d3b186..aa78e6fccf89 100644
--- a/scripts/nix-profile-daemon.sh.in
+++ b/scripts/nix-profile-daemon.sh.in
@@ -6,15 +6,6 @@ export NIX_USER_PROFILE_DIR="@localstatedir@/nix/profiles/per-user/$USER"
 export NIX_PROFILES="@localstatedir@/nix/profiles/default $HOME/.nix-profile"
 
 if test -w $HOME; then
-  if ! test -L $HOME/.nix-profile; then
-      if test "$USER" != root; then
-          ln -s $NIX_USER_PROFILE_DIR/profile $HOME/.nix-profile
-      else
-          # Root installs in the system-wide profile by default.
-          ln -s @localstatedir@/nix/profiles/default $HOME/.nix-profile
-      fi
-  fi
-
   # Set up a default Nix expression from which to install stuff.
   if [ ! -e $HOME/.nix-defexpr -o -L $HOME/.nix-defexpr ]; then
       rm -f $HOME/.nix-defexpr
diff --git a/scripts/nix-profile.sh.in b/scripts/nix-profile.sh.in
index 8567f5125857..ed4d1a6393f9 100644
--- a/scripts/nix-profile.sh.in
+++ b/scripts/nix-profile.sh.in
@@ -8,18 +8,6 @@ if [ -n "$HOME" ] && [ -n "$USER" ]; then
     NIX_USER_PROFILE_DIR=@localstatedir@/nix/profiles/per-user/$USER
 
     if [ -w "$HOME" ]; then
-        if ! [ -L "$NIX_LINK" ]; then
-            echo "Nix: creating $NIX_LINK" >&2
-            if [ "$USER" != root ]; then
-                if ! ln -s "$NIX_USER_PROFILE_DIR"/profile "$NIX_LINK"; then
-                    echo "Nix: WARNING: could not create $NIX_LINK -> $NIX_USER_PROFILE_DIR/profile" >&2
-                fi
-            else
-                # Root installs in the system-wide profile by default.
-                ln -s @localstatedir@/nix/profiles/default "$NIX_LINK"
-            fi
-        fi
-
         # Set up a default Nix expression from which to install stuff.
         __nix_defexpr="$HOME"/.nix-defexpr
         [ -L "$__nix_defexpr" ] && rm -f "$__nix_defexpr"
diff --git a/src/libstore/local-store.cc b/src/libstore/local-store.cc
index 6d2e21b931a9..d4f4cdae149e 100644
--- a/src/libstore/local-store.cc
+++ b/src/libstore/local-store.cc
@@ -70,16 +70,17 @@ LocalStore::LocalStore(const Params & params)
         createSymlink(profilesDir, gcRootsDir + "/profiles");
     }
 
+    for (auto & perUserDir : {profilesDir + "/per-user", gcRootsDir + "/per-user"}) {
+        createDirs(perUserDir);
+        if (chmod(perUserDir.c_str(), 0755) == -1)
+            throw SysError("could not set permissions on '%s' to 755", perUserDir);
+    }
+
+    createUser(getUserName(), getuid());
+
     /* Optionally, create directories and set permissions for a
        multi-user install. */
     if (getuid() == 0 && settings.buildUsersGroup != "") {
-
-        for (auto & perUserDir : {profilesDir + "/per-user", gcRootsDir + "/per-user"}) {
-            createDirs(perUserDir);
-            if (chmod(perUserDir.c_str(), 0755) == -1)
-                throw SysError("could not set permissions on '%s' to 755", perUserDir);
-        }
-
         mode_t perm = 01775;
 
         struct group * gr = getgrnam(settings.buildUsersGroup.get().c_str());
diff --git a/src/libutil/util.cc b/src/libutil/util.cc
index 1b744999153a..6f3bf7ae86e3 100644
--- a/src/libutil/util.cc
+++ b/src/libutil/util.cc
@@ -475,6 +475,16 @@ Path createTempDir(const Path & tmpRoot, const Path & prefix,
 }
 
 
+std::string getUserName()
+{
+    auto pw = getpwuid(geteuid());
+    std::string name = pw ? pw->pw_name : getEnv("USER", "");
+    if (name.empty())
+        throw Error("cannot figure out user name");
+    return name;
+}
+
+
 static Lazy<Path> getHome2([]() {
     Path homeDir = getEnv("HOME");
     if (homeDir.empty()) {
diff --git a/src/libutil/util.hh b/src/libutil/util.hh
index 07c3d28ff2d6..f057fdb2c041 100644
--- a/src/libutil/util.hh
+++ b/src/libutil/util.hh
@@ -126,6 +126,8 @@ void deletePath(const Path & path, unsigned long long & bytesFreed);
 Path createTempDir(const Path & tmpRoot = "", const Path & prefix = "nix",
     bool includePid = true, bool useGlobalCounter = true, mode_t mode = 0755);
 
+std::string getUserName();
+
 /* Return $HOME or the user's home directory from /etc/passwd. */
 Path getHome();
 
diff --git a/src/nix-channel/nix-channel.cc b/src/nix-channel/nix-channel.cc
index 06eb3d23ba83..70aa5c96669d 100755
--- a/src/nix-channel/nix-channel.cc
+++ b/src/nix-channel/nix-channel.cc
@@ -159,13 +159,7 @@ static int _main(int argc, char ** argv)
         nixDefExpr = home + "/.nix-defexpr";
 
         // Figure out the name of the channels profile.
-        ;
-        auto pw = getpwuid(geteuid());
-        std::string name = pw ? pw->pw_name : getEnv("USER", "");
-        if (name.empty())
-            throw Error("cannot figure out user name");
-        profile = settings.nixStateDir + "/profiles/per-user/" + name + "/channels";
-        createDirs(dirOf(profile));
+        profile = fmt("%s/profiles/per-user/%s/channels", settings.nixStateDir, getUserName());
 
         enum {
             cNone,
diff --git a/src/nix-env/nix-env.cc b/src/nix-env/nix-env.cc
index 87b2e43f063d..c7b6bdaafbc2 100644
--- a/src/nix-env/nix-env.cc
+++ b/src/nix-env/nix-env.cc
@@ -1425,9 +1425,14 @@ static int _main(int argc, char * * argv)
 
         if (globals.profile == "") {
             Path profileLink = getHome() + "/.nix-profile";
-            globals.profile = pathExists(profileLink)
-                ? absPath(readLink(profileLink), dirOf(profileLink))
-                : canonPath(settings.nixStateDir + "/profiles/default");
+            if (!pathExists(profileLink)) {
+                replaceSymlink(
+                    getuid() == 0
+                    ? settings.nixStateDir + "/profiles/default"
+                    : fmt("%s/profiles/per-user/%s/profile", settings.nixStateDir, getUserName()),
+                    profileLink);
+            }
+            globals.profile = absPath(readLink(profileLink), dirOf(profileLink));
         }
 
         op(globals, opFlags, opArgs);
diff --git a/tests/nix-channel.sh b/tests/nix-channel.sh
index 55f1695c4412..93f837befcec 100644
--- a/tests/nix-channel.sh
+++ b/tests/nix-channel.sh
@@ -36,7 +36,7 @@ grep -q 'item.*attrPath="foo".*name="dependencies"' $TEST_ROOT/meta.xml
 
 # Do an install.
 nix-env -i dependencies
-[ -e $TEST_ROOT/var/nix/profiles/default/foobar ]
+[ -e $TEST_HOME/.nix-profile/foobar ]
 
 clearProfiles
 rm -f $TEST_HOME/.nix-channels
@@ -55,5 +55,5 @@ grep -q 'item.*attrPath="foo".*name="dependencies"' $TEST_ROOT/meta.xml
 
 # Do an install.
 nix-env -i dependencies
-[ -e $TEST_ROOT/var/nix/profiles/default/foobar ]
+[ -e $TEST_HOME/.nix-profile/foobar ]
 
diff --git a/tests/nix-profile.sh b/tests/nix-profile.sh
index b808cf1b4632..e2e0d1090804 100644
--- a/tests/nix-profile.sh
+++ b/tests/nix-profile.sh
@@ -7,5 +7,3 @@ rm -rf $TEST_HOME $TEST_ROOT/profile-var
 mkdir -p $TEST_HOME
 USER=$user $SHELL -e -c ". $TEST_ROOT/nix-profile.sh; set"
 USER=$user $SHELL -e -c ". $TEST_ROOT/nix-profile.sh" # test idempotency
-
-[ -L $TEST_HOME/.nix-profile ]