-
Notifications
You must be signed in to change notification settings - Fork 2.4k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Distinguish lockfile version req from normal dep in resolver error message #9847
Conversation
r? @ehuss (rust-highfive has picked a reviewer for you, use r? to override) |
TODO?
|
r? @Eh2406 |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This looks much like what I had in mind. Thank you!
I do want either @alexcrichton or @ehuss to double check that this is something we want. I came up with the idea, but I have missed things in the past.
@@ -49,22 +51,48 @@ impl OptVersionReq { | |||
cmp.op == Op::Exact && cmp.minor.is_some() && cmp.patch.is_some() | |||
} | |||
} | |||
OptVersionReq::Locked(..) => true, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Is the is_exact
method still used anywhere? If sow why?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
IIUC, for cargo install
to decide whether to skip registry update or not. Though I found that some other duplicated logic laying there. 😂
https://github.com/rust-lang/cargo/pull/9847/files#diff-085d4f28bd6e49633caa467300082e94527f840dd487242b13bad2882a25451fR678
src/cargo/util/semver_ext.rs
Outdated
} | ||
} | ||
|
||
pub fn matches(&self, version: &Version) -> bool { | ||
match self { | ||
OptVersionReq::Any => true, | ||
OptVersionReq::Req(req) => req.matches(version), | ||
OptVersionReq::Locked(v, _) => VersionReq::exact(v).matches(version), |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can thes just be v == version
? Or are there problems with the metadata part? Are there test to make sure we don't accidentally switch to the "simpler code" if it does not work?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yes the metadata is counted in when comparing two Version
s. We can reimplement the logic from our side since it is simple, but I am uncertain whether it is appropriate to do that.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I've updated the logic with 4ecb543. The test cases are shamelessly copied from semver crate. Do you think it works?
FWIW to me this seems like a great idea. I agree though that it'd be best to reduce the dependence on |
`OptVersionReq::Locked` stores the original version requirement and the acutal locked version. This makes error message describing more precise.
Previously we use exact semver version req to synthesize locked version req. Now we make those need a truly locked to be `OptVersionReq::Locked`.
When encounter resolver error with locked dependency, we now show original version req along with the exact locked version.
Instead of creating another VersionReq, this can reduce some extra efforts on version matching logic. Though it also may introduces divergence from semver's matching logic. Accordingly, we borrow unit tests from semver crate and compare the matching results to prevent future breaks.
66fcbdd
to
4ecb543
Compare
I am sorry. I dropped the ball on this. It looks like Alex like the approach. @weihanglo did you have more clean ups in mind? Do you think this is ready to merge? |
Yep, @Eh2406. I think after 4ecb543 and 725420e, it should be ready to merge. One thing I am not sure is how to create a test case for the "(locked to a.b.c)" message? There is one already but do we need a dedicated one? |
Tests for the resolver error messages are woefully lacking. So, having one test that can see the change in behavior feels adequate. If you feel like adding more tests (in another PR) I would not object! Thank you for working on this! |
📌 Commit 725420e has been approved by |
☀️ Test successful - checks-actions |
Update cargo 7 commits in d56b42c549dbb7e7d0f712c51b39400260d114d4..c7957a74bdcf3b11e7154c1a9401735f23ebd484 2021-09-27 13:44:18 +0000 to 2021-10-11 20:17:07 +0000 - Add some more information to verbose version. (rust-lang/cargo#9968) - Skip all `cargo fix` that tends to write to registry cache. (rust-lang/cargo#9938) - Stabilize named profiles (rust-lang/cargo#9943) - Update git2 (rust-lang/cargo#9963) - Distinguish lockfile version req from normal dep in resolver error message (rust-lang/cargo#9847) - nit: Allocated slightly bigger vec than needed (rust-lang/cargo#9954) - Add shell completion for shorthand commands (rust-lang/cargo#9951)
If there's a version in the lock file only use that exact version ### What does this PR try to resolve? Generally, cargo is of the opinion that semver metadata should be ignored. It's is relevant to dependency resolution as any other description of the version, just like the description field in cargo.toml. If your registry has two versions that only differing metadata you get the bugs you deserve. We implement functionality to make it easier for our users or for us to maintain. ~~So let's use `==` because it's less code to write and test.~~ We also believe that lock files should ensure reproducibility and protect against mutations from the registry. In this circumstance these two goals are in conflict, and this PR picks reproducibility. If the lock file tells us that there is a version called `1.0.0+bar` then we should not silently use `1.0.0+foo` even though they have the same version. This is one of the alternatives/follow-ups discussed in #11447. It was separated from #12749, to allow for separate discussion and because I was being too clever by half. ### How should we test and review this PR? All tests still pass except for the ones that were removed. The removed tests were only added to verify the on intuitive behavior of the older implementation in #9847.
Resolves #9840
This PR adds a new variant
OptVersionReq::Locked
as #9840 described.The new variant represents as a locked version requirement that contains
an exact locked version and the original version requirement.
Previously we use exact version req to synthesize locked version req.
Now we make those need a truly locked to be
OptVersionReq::Locked
,including:
[patch]
: previous used exact version req to emulate locked version,and it only need to lock dep version but not source ID, so we make
an extra method
Dependency::lock_version
for it.