How to disable nix-env?

I am using NixOS to deploy multiple machines using nix-deploy. This works very well and the reproducibility helps a lot. However, I have noticed that people started using nix-env to install utilities like e.g. tcpdump. As nix-env does not auto-update packages, I want people to instead use nix-shell or add packages to the NixOS system configuration. To enforce this, I want to disable nix-env.

I have checked the NixOS options and the nix/nixpkgs issue tracker but have not found an easy way to do this. Has anybody already done something like this or an idea how to achieve this?

Philipp

Not sure about disabling nix-env but this may be useful for your use case:

  # directly run the missing commands via nix-shell (without installing anything)
  programs.command-not-found.enable = true;
  environment.variables.NIX_AUTO_RUN = "1";

If you are using home-manager you can also do something like this (do NOT use this as is on macOS):

  # remove all packages installed by `nix-env`
  home.activation = {
    uninstallPackages = lib.hm.dag.entryAfter [ "writeBoundary" ] ''
      $DRY_RUN_CMD nix-env $VERBOSE_ARG --uninstall $(nix-env -q | grep -v home-manager-path)
    '';
  };
1 Like

I don’t think we have a way to do this easily right now. You could try making /nix/var/nix/profiles/per-user/ read-only though.

you may also wrap nix-env with a warning. Here’s an example:

with import <nixpkgs> {};
lib.hiPrio (writeScriptBin "nix-env" ''
  NIX="$(${coreutils}/bin/readlink -f $(which nix-build))"
  NIX="$(${coreutils}/bin/dirname "$NIX")"

  echo THIS IS A WARNING

  exec "$NIX/nix-env" "$@"
'')

Just add this package to environment.systemPackages and it will override nix-env. It doesn’t disable nix-env completely though.

2 Likes

Thanks for the suggestions. I think I will give the wrapper approach a try, that seems the least invasive one. I will report how it goes.