Qt development environment on a flake system

The issue with nix-shell is while it was convenient, it was doing a lot of magic in the background that was extremely confusing. In addition, it hard depends on Nixpkgs, which is annoying.

Since one of the goals of the new nix command is to be consistent and easily understandable, the ability to string up an ad-hoc shell derivation from arguments had to be removed. At least until an acceptable interface is designed.

If I wanted simple, I would create a tiny shell.nix using mkShell similar to above and enter it with nix-shell:

{
  pkgs ? import <nixpkgs> {},
}:

pkgs.mkShell {
  nativeBuildInputs = with pkgs; [
    libsForQt5.qt5.qmake
  ];
  buildInputs = with pkgs; [
    libsForQt5.qt5.qtserialport
  ];
}

But personally, I prefer pinning the Nixpkgs and other dependencies. I would choose the experimental flakes for that, even though flake.nix requires a bit more boilerplate:

{
  description = "My Qt app";

  inputs = {
    nixpkgs.url = "github:NixOS/nixpkgs/nixpkgs-unstable";
  };

  outputs = { self, nixpkgs }:
    let
      system = "x86_64-linux";

      pkgs = import nixpkgs {
        inherit system;
        config = { };
      };
    in {
      devShells.${system}.default = pkgs.mkShell {
        nativeBuildInputs = with pkgs; [
          libsForQt5.qt5.qmake
        ];
        buildInputs = with pkgs; [
          libsForQt5.qt5.qtserialport
        ];
      };
    };
}

That might have been due to environment contamination from e.g. your terminal emulator or the desktop environment. Unfortunately, since we control the Qt runtime with environment variables, they will get inherited. Even when the app is built against a different version of libraries.

I would recommend doing the wrapping hack in any case:

pkgs.mkShell {
  nativeBuildInputs = with pkgs; [
    libsForQt5.qt5.qmake

    # For setting Qt environment variables.
    qt5.wrapQtAppsHook
    makeWrapper
  ];

  buildInputs = with pkgs; [
    libsForQt5.qt5.qtserialport
  ];

  shellHook = ''
    # Add Qt-related environment variables.
    # https://discourse.nixos.org/t/python-qt-woes/11808/10
    setQtEnvironment=$(mktemp)
    random=$(openssl rand -base64 20 | sed "s/[^a-zA-Z0-9]//g")
    makeWrapper "$(type -p sh)" "$setQtEnvironment" "''${qtWrapperArgs[@]}" --argv0 "$random"
    sed "/$random/d" -i "$setQtEnvironment"
    source "$setQtEnvironment"
  '';
}
4 Likes