Basic nix devShell for python and streamlit

Hi, noob question here. I’m new to the Nix ecosystem and I’m trying to spin up a python & streamlit project within a Nix dev shell.

I manage to successfully enter the shell and have access to Streamlit, version 1.21.0. However, I can’t load any of the python modules I need (matplotlib, pandas, …) and I get this error after trying to import X as Y. Error: Original error was: No module named 'numpy.core._multiarray_umath'

Any idea of what is going wrong?? I’d appreciate any help :slight_smile:

My flake.nix looks like this:

{
  description = "Starting to try good Ops procedures w/ Nix";

  inputs.nixpkgs.url = "github:nixos/nixpkgs/nixos-23.05";

  outputs = { self, nixpkgs }:
    let
      pkgs = import nixpkgs {
        system = "x86_64-linux";
      };
      pythonPackages = pkgs.python311Packages;
      pyPkgs = with pythonPackages; [
        pandas
        matplotlib
        numpy
        plotly
        seaborn
      ];
    in
    {
      devShells.x86_64-linux = {
        default = pkgs.mkShell {
          buildInputs = [ 
            pyPkgs
            pkgs.streamlit 
            pkgs.cowsay 
          ];
        };
      };
    };
}
1 Like

The reason for this is that the python you’re calling in the terminal is still the one from your system; it doesn’t know about any of the packages you installed with nix.

Nixpkgs has a mechanism called withPackages that allows you to install a separate version of python that does know about them, though.

First, change your definition of pyPkgs:

      pyPkgs = pythonPackages: with pythonPackages; [
        pandas
        matplotlib
        numpy
        plotly
        seaborn
      ];

And your build inputs to

          buildInputs = [ 
            (pkgs.python3.withPackages pyPkgs)
            pkgs.streamlit 
            pkgs.cowsay 
          ];

You can find more info in the NixOS wiki entry on Python.

3 Likes

I believe you can also just include pkgs.python3 in the list of buildInputs and the python3 package will include the other python packages your shell depends on when it builds its PYTHONPATH (link to wrapper)

You can also check if you’re invoking a Nix-aware python in your nix develop shell with:
$ command -v python
You should see a Nix store path instead of /usr/bin/python

3 Likes

@achooie I’ve tried this buildInputs = [ pkgs.python3 pyPkgs … ] but didn’t fix it. The solution above by @iFreilicht worked though. Also $ command -v python3 was always pointing to a Nix store path, so I’m not quite sure why it wasn’t working… Thanks

worked like a charm! Thanks!!!

1 Like

Awesome! I looked at streamlit now, and the reason you had python from nixpkgs available is that it’s a dependency of streamlit.

@achooie I think that might work when passing the python packages to buildEnv.extraLibs. That’s pretty much all that withPackages does, anyway.

1 Like

Dang, I thought I knew something. Sorry!

1 Like