This commit fixes a bug introduced in #276 where symlinked Cargo.tomls
wouldn't get detected due to readDir() reporting them as - well -
_symlinks_ instead of regular files.
Note that we continue to keep the `if type == "directory"` condition for
recursion which means that we'll fail to detect "nested" Cargo.tomls if
someone decides to go wild and create workspace with symlinked crates.
That I'm not 100% sure on how to approach, but fortunately cases like
those seem to be practically non-existent (and Crane apparently not
supporting them builds a bit of confidence here as well).
Closes#280.
Our current Cargo.toml discovery algorithm is based on reading the main
Cargo.toml and looking at its `workspace.members` - unfortunately, as it
turns out there's actually no requirement for all workspace crates to be
listed there, and some applications do fancy things like:
```toml
[workspace]
members = [ "crates/foo" ]
[dependencies]
foo = { path = "crates/foo" }
bar = { path = "crates/bar" } # whoopsie
```
... which doesn't play nice with Naersk's incremental builds (that is,
the compilation fails unless `singleStep = true;` is turned on).
This commit changes the logic to use a different approach: now we simply
recursively scan the root directory, noting down all the Cargo.tomls we
find; Crane seems to use the same algorithm.
I think the only case where this approach falls short are spurious
Cargo.tomls that are present somewhere in the source directory but are
actually unused - for instance, imagine I'm writing a Cargo clone where
I've got files like `src/tests/broken-manifest/Cargo.toml` - in cases
like these, the current approach will cause the build to fail, because
we will try to fixup a broken Cargo.toml, thinking it's used somewhere.
We could try to handle cases like these by using an even different
approach: instead of traversing the source tree, we could load the main
Cargo.toml and traverse its `workspace.members` + all path-based
dependencies recursively, noting down all the *explicitly present*
Cargo.tomls.
That is, given a top-level manifest of:
```
[workspace]
members = [ "crates/foo" ]
[dependencies]
foo = { path = "crates/foo" }
bar = { path = "crates/bar" }
```
... we'd note down and load `crates/foo/Cargo.toml` +
`crates/bar/Cargo.toml`, and then load _their_ path-based dependencies,
to find all transitive Cargo.tomls that belong to this workspace.
(that is, we have to scan the crates recursively, because `bar` might
depend on `crates/zar` - and that's not an imaginary edge case, that's
actually what happens inside Nushell, for instance.)
I don't have enough time to implement this more extensive approach now,
and IMO the improvement presented here is still an improvement, so I
think it's safe to go with the new-but-still-subpar approach here and
consider the better algorithm in the future :-)
# Testing
All tests pass, I've also made sure that incremental builds are still
incremental.
Closes https://github.com/nix-community/naersk/issues/274
Prevent use of allRefs when nix <2.4 is in use.
nix <2.4 does not accept the `allRefs` flag, but has `allRefs` behavior
by default. Note that this goes beyond the the initial intent of this
PR because it enables naersk's `gitAllRefs` flag to work on nix <2.4.
The usage of git "rev" dependencies in Cargo implies that the rev
will be found regardless of ref. This is currently not true in naersk;
the following dependency fails:
usbfs = {git = "https://github.com/goertzenator/usbfs-rs", rev = "7c35b46e41ad76f838cd99b493f9337f475b5b70"}
During compilation, we build two derivations - one for the dependencies
and another for the user's crate itself. Passing `postInstall` to
`buildPackage` pass-throughs it into both derivations, which is not what
most users would probably expect.
This commit adds `postInstall` as an explicit configuration option (so
that it's neatly documented), zeroing it out for the dependencies-only
derivation.
I don't think there's any use case for something like `postInstallDeps`,
so it's not introduced here.
Closes https://github.com/nix-community/naersk/issues/237
When a dependency gets fetched from Git, it's possible for its name to
contain slashes - e.g. because the dependency's branch name contains
one:
```
something-something = { git = "...", branch = "JIRA-123/dev" }
```
Currently, because we don't sanitize those slashes, trying to compile
such `Cargo.toml` / `Cargo.lock` would fail - e.g. given a dependency
from branch `JIRA-123/dev`, we'd try to extract it into path
`JIRA-123/dev` instead of something flat such as `JIRA-123_dev`.
This commit fixes this issue by sanitizing all the `nkey`s - basically,
for all dependency paths, we replace `/` with `_`.
The choice of underscore is arbitrary, just seemed like a good fit.
Without this change you'd get errors like this when adding a
`git`-dependency to a `Cargo.toml` which is pinned to a tag:
fetching Git repository 'git://github.com/ma27/nixpkgs-fmt'fatal: couldn't find remote ref refs/heads/v1.2.0-rnix-0.10
error: program 'git' failed with exit code 128
* Update to a more recent revision of nixpkgs
* Add nixpkgs-21.11 for testing
* Add nixpkgs-21.05 for testing
* Drop nixpkgs-20.09, branch is EOL
* Drop nixpkgs-20.05, branch is EOL
* Bump ripgrep-all to v0.9.6 to make tests pass