Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Single Admin user & multiple non-admin users #119

Open
lougreenwood opened this issue Oct 22, 2024 · 1 comment
Open

Single Admin user & multiple non-admin users #119

lougreenwood opened this issue Oct 22, 2024 · 1 comment
Labels
question Further information is requested

Comments

@lougreenwood
Copy link

I've been watching this project for some time now, looks very cool & interesting!

Currently I have my own custom blueprint system which is based on homebrew, mackup, dotbot & transcrypt as well as many custom scripts.

As part of my system setup I always create a separate admin user and then all of my day-to-day users are non-admin.

This means that I always need to install things with homebrew as an admin user.

❓ So my question is...

  • Does this config support multiple users which are a mix of admin & non-admin
  • If so, does it support classes of users? For example:
    • I have configs for my "programming" user which setups up a bunch of env & tooling for programming work
    • My admin user doesn't need any of this stuff, so has a much simpler config for zsh etc
    • I have other users which run on home servers where I run VMs, again, these users don't need programming-specific config
  • Does it support installing homebrew as the admin user so that only the admin owns homebrew packages and other users must sudo to install stuff with brew?

I tried searching the repo, I see that there is a trusted_user thing and it seems that there is other stuff related to user info etc... but without diving into the setup I figured it might be easier to ask it here and then there is some documentation for future users.

Thanks!!

@dustinlyons
Copy link
Owner

Hi @lougreenwood

Thanks for the kind words on the project!

Here is where I setup the user:

users.users.${user} = {

The trusted-users setting is only used to specify some additional permissions on the Nix daemon, such as the ability to specify additional binary caches, or import unsigned code. It doesn't manage sudo.

You could do something like this (I haven't tested it):

{
  # Define the "admin" user with root-like privileges
  users.users.admin = {
    isNormalUser = true;
    home = "/home/admin";
    extraGroups = [ "wheel" ]; # wheel group allows sudo access
    hashedPassword = "<hashed-password>"; # You can set a hashed password here or use `passwordFile` or `password` directly for simplicity
    shell = pkgs.bashInteractive; # You can specify any shell here
  };

  # Define a less privileged user, "standard"
  users.users.standard = {
    isNormalUser = true;
    home = "/home/standard";
    hashedPassword = "<hashed-password>";
    shell = pkgs.bashInteractive;
  };

  # Ensure sudo privileges for members of the "wheel" group
  security.sudo = {
    enable = true;
    wheelNeedsPassword = true; # Members of the wheel group must provide a password for sudo
  };

  # Setup user packages, programs, and nix settings
  nix = {
    package = pkgs.nix;
    configureBuildUsers = true;

    settings = {
      trusted-users = [ "@admin" "root" "standard" ];
      substituters = [ "https://nix-community.cachix.org" "https://cache.nixos.org" ];
      trusted-public-keys = [ "cache.nixos.org-1:6NCHdD59X431o0gWypbMrAURkbJ16ZPMQFGspcDShjY=" ];
    };

    gc = {
      user = "root";
      automatic = true;
      interval = { Weekday = 0; Hour = 2; Minute = 0; };
      options = "--delete-older-than 30d";
    };

    extraOptions = ''
      experimental-features = nix-command flakes
    '';
  };
}

For managing different software for different users, I'd look into breaking out home-manager a bit more. You would have multiple lines here:

users.${user} = import ./modules/nixos/home-manager.nix;

Don't get confused by the ${user}, that just gets replaced with dustin, my user. I could just as easily have written users.dustin.

For how to break it out, I asked ChatGPT how to do it and here's what it said:

To ensure different users on a macOS system receive distinct packages and settings declaratively with nix-darwin and home-manager, we can set up separate configurations for each user. Let’s walk through how this setup works and how each user would get a tailored environment upon logging in.

1. Organize User-Specific Configuration Files

First, you need separate files for each user’s configuration, specifying packages and any custom settings they need. For example:

  • users/dustin.nix for the user dustin
  • users/otheruser.nix for another user, otheruser

Each of these files will define the packages and settings unique to that user. Here’s an example structure for dustin.nix:

{ config, pkgs, ... }:

{
  home-manager.users.dustin = { pkgs, ... }: {
    # Packages specific to user "dustin"
    home.packages = with pkgs; [
      emacs
      git
      tmux
    ];

    # Additional user-specific settings go here
  };
}

For otheruser.nix, you’d specify the configuration specific to otheruser:

{ config, pkgs, ... }:

{
  home-manager.users.otheruser = { pkgs, ... }: {
    # Packages specific to "otheruser"
    home.packages = with pkgs; [
      nano
      htop
      wget
    ];

    # Additional user-specific settings go here
  };
}

2. Integrate User Modules into darwinConfigurations

In your main flake configuration, reference these user modules within darwinConfigurations. This setup will link each user’s configuration to their profile in a declarative manner.

Here’s how you’d adjust the darwinConfigurations section to incorporate the different user-specific modules:

darwinConfigurations = nixpkgs.lib.genAttrs darwinSystems (system:
  darwin.lib.darwinSystem {
    inherit system;
    specialArgs = inputs;
    modules = [
      # Load the home-manager module for macOS
      home-manager.darwinModules.home-manager

      # Load nix-homebrew for macOS
      nix-homebrew.darwinModules.nix-homebrew

      # Homebrew settings (applicable to all users on macOS)
      {
        nix-homebrew = {
          inherit user;
          enable = true;
          taps = {
            "homebrew/homebrew-core" = homebrew-core;
            "homebrew/homebrew-cask" = homebrew-cask;
            "homebrew/homebrew-bundle" = homebrew-bundle;
          };
          mutableTaps = false;
          autoMigrate = true;
        };
      }

      # Base macOS host configurations
      ./hosts/darwin

      # User-specific modules
      ./users/dustin.nix
      ./users/otheruser.nix
    ];
  }
);

3. Login and Home-Manager Activation for Each User

Once this setup is applied, here’s what will happen for each user:

  • Login for dustin: When dustin logs in, home-manager will activate his configuration based on the home-manager.users.dustin block in dustin.nix. This configuration includes his custom packages (emacs, git, tmux, etc.), so they’ll be available in his environment. Home-manager links these packages into his $HOME/.nix-profile/bin directory.

  • Login for otheruser: When otheruser logs in, home-manager activates their configuration from otheruser.nix, making only their specified packages (nano, htop, wget, etc.) available.

4. Home-Manager Execution and Profile Activation

For each user:

  • home-manager symlinks their configuration to $HOME/.nix-profile.
  • Any packages or custom settings defined in their specific configuration file are activated upon login. You can run home-manager switch for the user to apply changes immediately or use home-manager to set up a login hook that automatically activates the environment on each login.

Summary of the Flow

  1. Configure: Each user has a dedicated .nix file (dustin.nix, otheruser.nix) with their packages and settings.
  2. Integrate: The main flake config includes all user configurations under darwinConfigurations.
  3. Activate: Upon login, home-manager activates the configuration for each user, linking packages into their environment.

Notes

  • To test user-specific configurations, you can use su to switch to different users and run home-manager switch to see changes.
  • If using a session manager that supports user-specific home-manager hooks, consider setting up an automatic home-manager switch on login to ensure configurations stay updated.

This setup maintains a clear, declarative, and reproducible environment for each user on macOS with Nix flakes, nix-darwin, and home-manager.

@dustinlyons dustinlyons added the question Further information is requested label Oct 31, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
question Further information is requested
Projects
None yet
Development

No branches or pull requests

2 participants