timbertson / opam2nix

Generate nix expressions from opam packages
MIT License
93 stars 28 forks source link

generating opam-selection.nix requires write access to /nix/store #22

Closed ehmry closed 4 years ago

ehmry commented 4 years ago

I would like to use opam2nix to build Mirage unikernels. I can build the mirage utility fine, but the build process of the unikernels themselves involves generating an OPAM description using mirage, which should be further processed by opam2nix.

Ideally there would be a complete graph of Nix builds to do this, building the Mirage tool, generating OPAM, generating opam-selection.nix, importing, and building the application. The problem is that opam2nix is writing to the store when invoked and thus fails within the Nix sandbox.

Is this avoidable? Where is this happening during resolving?

timbertson commented 4 years ago

Hmm, I'm guessing this might be nix_digest_of_path which uses nix-store --dump.

If so, that's used for:

The second part is an optimisation, so that changing opam-repository doesn't force a rebuild of all packages, only the packages whose contents differ. So that could be skipped in theory (but would lead to excess rebuilding)

None of this feels essential that it actually write to the store path though. There should be a different command which generates the same digests but doesn't actually write to the store. Resulting in potential double-downloading of opam-repository, but that's not the worst.

I'd need to be able to reproduce to see what the actual issue is though, do you have some minimal reproduction steps? (not promising I can tend to it soon unfortunately)

ehmry commented 4 years ago

I made a little test and actually the builder fails because git is missing, permission denied errors were not critical.

A test builder:

{ pkgs ? import <nixpkgs> { }

, opam2nix ? import (builtins.fetchTarball
  "https://github.com/timbertson/opam2nix/archive/v1.tar.gz") { } }:

pkgs.runCommand "opam2nix-test" {
  outputHashAlgo = "sha256";
  outputHashMode = "recursive";
  outputHash = pkgs.lib.fakeSha256;
  buildInputs = [ opam2nix ];
} ''
  export HOME=$NIX_BUILD_TOP
  mkdir $out; cd $out
  opam2nix resolve sexplib
''

Build log:

trace: [wrangle] Providing source self (git-local) from /nix/store/9k5kc76r8fl00b9lm70j72z7rgaykrls-1g0klq9h7h8px3fci51a6hnygq3cbw1s-source
+ /nix/store/273l0q1gpgjpwsivjc4nk2648wpnf8d8-opam2nix-1.0.0/bin/opam2nix resolve sexplib
Using current <nixpkgs> ocaml version, pass --ocaml-version to override
Cloning https://github.com/ocaml/opam-repository.git...
 + git clone https://github.com/ocaml/opam-repository.git /build/.cache/opam2nix/opam-repository
error: creating directory '/nix/var': Permission denied
Fatal error: exception Failure("git clone https://github.com/ocaml/opam-repository.git /build/.cache/opam2nix/opam-repository failed")
timbertson commented 4 years ago

Ah good find, thanks