Skip to content

Commit

Permalink
Expand the multi-user installer to support Linuxes with systemd
Browse files Browse the repository at this point in the history
 - darwin installer: delete hardware report, not necessary
 - moves os-specific code from the darwin installer to to `poly_*`
   functions
 - adds profile.d support to the profile targets, which automatically
   handles many distros which don't have a /etc/bashrc but do have an
   /etc/profile.d
 - /bin/bash -> /usr/bin/env bash
 - document why each excluded shellcheck check is excluded
 - rename the multi-user to Daemon-based
grahamc committed Mar 29, 2018

Verified

This commit was signed with the committer’s verified signature.
EtiennePelletier Étienne Pelletier
1 parent 446bb88 commit 2921165
Showing 5 changed files with 1,063 additions and 760 deletions.
34 changes: 29 additions & 5 deletions release.nix
Original file line number Diff line number Diff line change
@@ -127,17 +127,39 @@ let
substitute ${./scripts/install-nix-from-closure.sh} $TMPDIR/install \
--subst-var-by nix ${toplevel} \
--subst-var-by cacert ${cacert}
substitute ${./scripts/install-darwin-multi-user.sh} $TMPDIR/install-darwin-multi-user \
substitute ${./scripts/install-darwin-multi-user.sh} $TMPDIR/install-darwin-multi-user.sh \
--subst-var-by nix ${toplevel} \
--subst-var-by cacert ${cacert}
substitute ${./scripts/install-systemd-multi-user.sh} $TMPDIR/install-systemd-multi-user.sh \
--subst-var-by nix ${toplevel} \
--subst-var-by cacert ${cacert}
substitute ${./scripts/install-multi-user.sh} $TMPDIR/install-multi-user \
--subst-var-by nix ${toplevel} \
--subst-var-by cacert ${cacert}
if type -p shellcheck; then
shellcheck -e SC1090 $TMPDIR/install
shellcheck -e SC1091,SC2002 $TMPDIR/install-darwin-multi-user
# SC1090: Don't worry about not being able to find
# $nix/etc/profile.d/nix.sh
shellcheck --exclude SC1090 $TMPDIR/install
shellcheck $TMPDIR/install-darwin-multi-user.sh
shellcheck $TMPDIR/install-systemd-multi-user.sh
# SC1091: Don't panic about not being able to source
# /etc/profile
# SC2002: Ignore "useless cat" "error", when loading
# .reginfo, as the cat is a much cleaner
# implementation, even though it is "useless"
# SC2116: Allow ROOT_HOME=$(echo ~root) for resolving
# root's home directory
shellcheck --external-sources \
--exclude SC1091,SC2002,SC2116 $TMPDIR/install-multi-user
fi
chmod +x $TMPDIR/install
chmod +x $TMPDIR/install-darwin-multi-user
chmod +x $TMPDIR/install-darwin-multi-user.sh
chmod +x $TMPDIR/install-systemd-multi-user.sh
chmod +x $TMPDIR/install-multi-user
dir=nix-${version}-${system}
fn=$out/$dir.tar.bz2
mkdir -p $out/nix-support
@@ -149,7 +171,9 @@ let
--transform "s,$TMPDIR/install,$dir/install," \
--transform "s,$TMPDIR/reginfo,$dir/.reginfo," \
--transform "s,$NIX_STORE,$dir/store,S" \
$TMPDIR/install $TMPDIR/install-darwin-multi-user $TMPDIR/reginfo \
$TMPDIR/install $TMPDIR/install-darwin-multi-user.sh \
$TMPDIR/install-systemd-multi-user.sh \
$TMPDIR/install-multi-user $TMPDIR/reginfo \
$(cat ${installerClosureInfo}/store-paths)
'');

831 changes: 78 additions & 753 deletions scripts/install-darwin-multi-user.sh

Large diffs are not rendered by default.

793 changes: 793 additions & 0 deletions scripts/install-multi-user.sh

Large diffs are not rendered by default.

11 changes: 9 additions & 2 deletions scripts/install-nix-from-closure.sh
Original file line number Diff line number Diff line change
@@ -29,8 +29,15 @@ if [ "$(uname -s)" = "Darwin" ]; then
exit 1
fi

printf '\e[1;31mSwitching to the Multi-User Darwin Installer\e[0m\n'
exec "$self/install-darwin-multi-user"
printf '\e[1;31mSwitching to the Daemon-based Installer\e[0m\n'
exec "$self/install-multi-user"
exit 0
fi

# Linux & Systemd support
if [ "$(uname -s)" = "Linux" ] && [ -e /run/systemd/system ]; then
printf '\e[1;31mSwitching to the Daemon-based Installer\e[0m\n'
exec "$self/install-multi-user"
exit 0
fi

154 changes: 154 additions & 0 deletions scripts/install-systemd-multi-user.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,154 @@
#!/usr/bin/env bash

set -eu
set -o pipefail

readonly SERVICE_SRC=/lib/systemd/system/nix-daemon.service
readonly SERVICE_DEST=/etc/systemd/system/nix-daemon.service

readonly SOCKET_SRC=/lib/systemd/system/nix-daemon.socket
readonly SOCKET_DEST=/etc/systemd/system/nix-daemon.socket

poly_validate_assumptions() {
if [ "$(uname -s)" != "Linux" ]; then
failure "This script is for use with Linux!"
fi
}

poly_service_installed_check() {
[ "$(systemctl is-enabled nix-daemon.service)" = "linked" ] \
|| [ "$(systemctl is-enabled nix-daemon.socket)" = "enabled" ]
}

poly_service_uninstall_directions() {
cat <<EOF
$1. Delete the systemd service and socket units
sudo systemctl stop nix-daemon.socket
sudo systemctl stop nix-daemon.service
sudo systemctl disable nix-daemon.socket
sudo systemctl disable nix-daemon.service
sudo systemctl daemon-reload
EOF
}

poly_service_setup_note() {
cat <<EOF
- load and start a service (at $SERVICE_DEST
and $SOCKET_DEST) for nix-daemon
EOF
}

poly_configure_nix_daemon_service() {
_sudo "to set up the nix-daemon service" \
systemctl link "/nix/var/nix/profiles/default$SERVICE_SRC"

_sudo "to set up the nix-daemon socket service" \
systemctl enable "/nix/var/nix/profiles/default$SOCKET_SRC"

_sudo "to load the systemd unit for nix-daemon" \
systemctl daemon-reload

_sudo "to start the nix-daemon.socket" \
systemctl start nix-daemon.socket

_sudo "to start the nix-daemon.service" \
systemctl start nix-daemon.service

}

poly_group_exists() {
getent group "$1" > /dev/null 2>&1
}

poly_group_id_get() {
getent group "$1" | cut -d: -f3
}

poly_create_build_group() {
_sudo "Create the Nix build group, $NIX_BUILD_GROUP_NAME" \
groupadd -g "$NIX_BUILD_GROUP_ID" --system \
"$NIX_BUILD_GROUP_NAME" >&2
}

poly_user_exists() {
getent passwd "$1" > /dev/null 2>&1
}

poly_user_id_get() {
getent passwd "$1" | cut -d: -f3
}

poly_user_hidden_get() {
echo "1"
}

poly_user_hidden_set() {
true
}

poly_user_home_get() {
getent passwd "$1" | cut -d: -f6
}

poly_user_home_set() {
_sudo "in order to give $1 a safe home directory" \
usermod --home "$2" "$1"
}

poly_user_note_get() {
getent passwd "$1" | cut -d: -f5
}

poly_user_note_set() {
_sudo "in order to give $1 a useful comment" \
usermod --comment "$2" "$1"
}

poly_user_shell_get() {
getent passwd "$1" | cut -d: -f7
}

poly_user_shell_set() {
_sudo "in order to prevent $1 from logging in" \
usermod --shell "$2" "$1"
}

poly_user_in_group_check() {
groups "$1" | grep -q "$2" > /dev/null 2>&1
}

poly_user_in_group_set() {
_sudo "Add $1 to the $2 group"\
usermod --append --groups "$2" "$1"
}

poly_user_primary_group_get() {
getent passwd "$1" | cut -d: -f4
}

poly_user_primary_group_set() {
_sudo "to let the nix daemon use this user for builds (this might seem redundant, but there are two concepts of group membership)" \
usermod --gid "$2" "$1"

}

poly_create_build_user() {
username=$1
uid=$2
builder_num=$3

_sudo "Creating the Nix build user, $username" \
useradd \
--home-dir /var/empty \
--comment "Nix build user $builder_num" \
--gid "$NIX_BUILD_GROUP_ID" \
--groups "$NIX_BUILD_GROUP_NAME" \
--no-user-group \
--system \
--shell /sbin/nologin \
--uid "$uid" \
--password "!" \
"$username"
}

0 comments on commit 2921165

Please sign in to comment.