How can a previous version of a program be specified in configuation.nix

I have NixOS installed and I would like to specify a previous version of a program in my configuration.nix file.

The reason why I want to use a previous version is because I have a printer that stoped working after I ran nixos-rebuild switch –upgrade.

I would like to specify a previous version of hplipWithPlugin to use in configuration.nix.

I looked at History for pkgs/misc/drivers/hplip/default.nix - NixOS/nixpkgs · GitHub and it looks like there are previous versions I could try. I think using a previous version may get the printer working again.

I would like to be able to do something like this in my configuaration.nix:
“””
environment.systemPackages = with pkgs; [ hplipWithPlugin@3.22.6 ];

#printer setup
services.printing.enable = true;
services.printing.drivers = [ pkgs.hplipWithPlugin@3.22.6 ];
services.avahi.enable = true;
“””

I just made up the hplipWithPlugin@3.22.6 syntax for saying the package at a specific version.

I have looked at these links but I am still not sure have to specify a previous version ao a program in configuration.nix:

https://nixos.org/manual/nixos/stable/#sec-package-management

https://nixos.wiki/wiki/FAQ/Pinning_Nixpkgs

Here is a link to a thread about the printer I am having trouble with:

Have you seen Nix package versions?

1 Like

@_Andrew thanks for sharing that link, it is interesting.

It is nice to see it say “Installing older versions of packages in Nix is easy”.

These two sections are interesting as it looks like how a previous version of a package could be specified:

“”"
Use hplip in a nix script via tarball

let
    pkgs = import (builtins.fetchTarball {
        url = "https://github.com/NixOS/nixpkgs/archive/02e464590ebd69ec541f0b9deea638b26e0dc0ac.tar.gz";
    }) {};

    myPkg = pkgs.hplip;
in
...

Use hplip in a nix script via Git

let
     pkgs = import (builtins.fetchGit {
         # Descriptive name to make the store path easier to identify
         name = "my-old-revision";
         url = "https://github.com/NixOS/nixpkgs/";
         ref = "refs/heads/nixos-23.11";
         rev = "02e464590ebd69ec541f0b9deea638b26e0dc0ac";
     }) {};

     myPkg = pkgs.hplip;
in
...

“”"

I am not sure how either of those would be used in a configuration.nix file for NixOS. I think I am missing an important part which is what is truncated by the ... parts.

You started with something like this—

{ pkgs, ... }:

{
  services.printing.drivers = [ pkgs.hplipWithPlugin ];
}

—and want to change pkgs.hplipWithPlugin. So that might look like:

{ pkgs, ... }:

let
  # Via https://lazamar.co.uk/nix-versions/?channel=nixos-23.11&package=hplip
  pkgs-2023-03-31 = import (builtins.fetchTarball { url = "https://github.com/NixOS/nixpkgs/archive/02e464590ebd69ec541f0b9deea638b26e0dc0ac.tar.gz"; }) { };
in
{
  services.printing.drivers = [ pkgs-2023-03-31.hplipWithPlugin ];
}
1 Like

@_Andrew thanks for that example.

When I make this change to my configuration.nix file:

let
  pkgs-2023-03-31 = import (builtins.fetchTarball { url = "https://github.com/NixOS/nixpkgs/archive/02e464590ebd69ec541f0b9deea638b26e0dc0ac.tar.gz"; }) { };
in

{
  services.printing.enable = true;
  services.printing.drivers = [ pkgs-2023-03-31.hplipWithPlugin ];
  services.avahi.enable = true;
}

and run nixos-rebuild switch --upgrade I get these error messages:

unpacking channels...
error:
       … while evaluating the attribute 'config'

         at /nix/store/i1pdnlk4ahqmkfx3is9gd6wc8qxlmzdl-nixos-23.11/nixos/lib/modules.nix:320:9:

          319|         options = checked options;
          320|         config = checked (removeAttrs config [ "_module" ]);
             |         ^
          321|         _module = checked (config._module);

       … while calling the 'seq' builtin

         at /nix/store/i1pdnlk4ahqmkfx3is9gd6wc8qxlmzdl-nixos-23.11/nixos/lib/modules.nix:320:18:

          319|         options = checked options;
          320|         config = checked (removeAttrs config [ "_module" ]);
             |                  ^
          321|         _module = checked (config._module);

       (stack trace truncated; use '--show-trace' to show the full trace)

       error: syntax error, unexpected LET

       at /etc/nixos/configuration.nix:337:3:

          336|
          337|   let
             |   ^
          338|     pkgs-2023-03-31 = import (builtins.fetchTarball { url = "https://github.com/NixOS/nixpkgs/archive/02e464590ebd69ec541f0b9deea638b26e0dc0ac.tar.gz"; }) { };
building Nix...
error:
       … while evaluating the attribute 'config'

         at /nix/store/i1pdnlk4ahqmkfx3is9gd6wc8qxlmzdl-nixos-23.11/nixos/lib/modules.nix:320:9:

          319|         options = checked options;
          320|         config = checked (removeAttrs config [ "_module" ]);
             |         ^
          321|         _module = checked (config._module);

       … while calling the 'seq' builtin

         at /nix/store/i1pdnlk4ahqmkfx3is9gd6wc8qxlmzdl-nixos-23.11/nixos/lib/modules.nix:320:18:

          319|         options = checked options;
          320|         config = checked (removeAttrs config [ "_module" ]);
             |                  ^
          321|         _module = checked (config._module);

       (stack trace truncated; use '--show-trace' to show the full trace)

       error: syntax error, unexpected LET

       at /etc/nixos/configuration.nix:337:3:

          336|
          337|   let
             |   ^
          338|     pkgs-2023-03-31 = import (builtins.fetchTarball { url = "https://github.com/NixOS/nixpkgs/archive/02e464590ebd69ec541f0b9deea638b26e0dc0ac.tar.gz"; }) { };
building the system configuration...
error:
       … while evaluating the attribute 'config.system.build.toplevel'

         at /nix/store/i1pdnlk4ahqmkfx3is9gd6wc8qxlmzdl-nixos-23.11/nixos/lib/modules.nix:320:9:

          319|         options = checked options;
          320|         config = checked (removeAttrs config [ "_module" ]);
             |         ^
          321|         _module = checked (config._module);

       … while calling the 'seq' builtin

         at /nix/store/i1pdnlk4ahqmkfx3is9gd6wc8qxlmzdl-nixos-23.11/nixos/lib/modules.nix:320:18:

          319|         options = checked options;
          320|         config = checked (removeAttrs config [ "_module" ]);
             |                  ^
          321|         _module = checked (config._module);

       (stack trace truncated; use '--show-trace' to show the full trace)

       error: syntax error, unexpected LET

       at /etc/nixos/configuration.nix:337:3:

          336|
          337|   let
             |   ^
          338|     pkgs-2023-03-31 = import (builtins.fetchTarball { url = "https://github.com/NixOS/nixpkgs/archive/02e464590ebd69ec541f0b9deea638b26e0dc0ac.tar.gz"; }) { };
1 Like

Hi, I think I’ve got the same result.
I thought there would be an easy way to install older versions of software on NixOS. I’m new and trying this here the first time.

As previously commented, this is the way:

Hi, I was referring to bluebull’s comment. I’ve got the same error. With tarball and github. I admit, this might be rather a more general skill issue with the configure script. I’m going to look myself for a more general solution.

If you’re getting that specific error, it’s probably because you put a let-expression directly inside an attribute set.

This is a binding:

name = expr;

This is a let-expression:

let
  name = expr;
in
expr2

This is an attribute set:

{
  name = expr;
}

Attribute sets can only contain bindings, not expressions. This is wrong:

{
  expr
}

And as a special case of above, so is this:

{
  let
    name = expr;
  in
  expr2
}

But this is okay, and probably what you want to do, because a let-expression is a kind of expression:

{
  name =
    let
      name2 = expr;
    in
    expr2;
}

This is also okay (because attribute sets are also expressions), and what you want if you want to share a let-binding among multiple attribute-bindings:

let
  name = expr;
in
{
  name2 = expr2;
}
1 Like

The thing is, copy and paste of the code from Nix package versions into a configuration.nix doesn’t work and it’s not explained how to use it.

let
    pkgs = import (builtins.fetchTarball {
        url = "https://github.com/NixOS/nixpkgs/archive/02e464590ebd69ec541f0b9deea638b26e0dc0ac.tar.gz";
    }) {};

    myPkg = pkgs.hplip;
in

It appears to be what you describe as “a let-expression” but it doesn’t accept it.

Last one I tested, after looking around in tutorials, was:

This before

{ config, pkgs, ... }:

  let
    pkgs-2023-03-31 = import (builtins.fetchTarball 
        { url = "https://github.com/NixOS/nixpkgs/archive/02e464590ebd69ec541f0b9deea638b26e0dc0ac.tar.gz"; }) { };

{

  imports =
....

And

users.users.user = {
    pkgsOLD = with pkgs-2023-03-31; [
        hplip];
...

Now there’s some confusion about “}” and I need a break.

I assure you that, provided you understand the syntax of the Nix language, you can copy the fragment from NPV into a configuration.nix and get good results. But you can’t simply paste it anywhere. Just like ‘I assure you that’ is not a complete sentence, let pkgs = whatever; in is not a complete Nix expression. But ‘I assure you that’ can be used correctly in a sentence, provided you don’t do I assure you that something confused, like this. Similarly, you have to choose the right place to insert let pkgs = whatever; in in your configuration.nix, by understanding the syntax and making sure that the result is a valid Nix expression.

It looks like you forgot the in keyword here.

It looks like you’re defining an attribute users.users.user.pkgsOLD here, which is not going to do you any good because that attribute isn’t a NixOS option.

An attribute-binding and a let-binding have identical syntax but do different things. An attribute-binding creates an attribute on an attribute set, and a let-binding creates a variable for you to use within that let-expression.

Okay, I’ll look into it at some time. Unfortunate that there’s no easier way. I’ll rather use some live distro running my old HP scanner for now, and the video editing (Flowblade) I wanted to try out was just meant as a test, so it can wait.