-
Notifications
You must be signed in to change notification settings - Fork 2.5k
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
Remove disabled optional weak dependencies from Cargo.lock #11938
Conversation
r? @epage (rustbot has picked a reviewer for you, use r? to override) |
8cda29d
to
48abb23
Compare
a0ccf26
to
850fb43
Compare
One clarification, I don't think I do not have enough implementation detail loaded into my brain at the moment to know if this is a problem, but any change to the |
Thanks for your reply, @Eh2406 !
I used "old" because of the explanation in the comments of the resolver module referring to the other one as the "new" one, so I inferred the other one would be the old one, but I will change the PR description. The issue with calling the new resolver as the feature aware one is that one might think that the
I will add more tests once I find time to work on this PR. |
That is entirely fair. It is the terminology we use then. And I am sorry for the confusion that terminology has caused over the years.
That makes sense. And I'm open to better terminology.
The |
Is there any other way to solve this problem now? |
I'm sorry if I wasn't clear. I do think this is a reasonable and correct approach. I think Ed had some concerns about exactly how we opt into it, and I would like to see more testing. But I am supportive of this work moving forward. |
From my perspective, if a new lockfile version is what is needed, ok. I was then waiting on a response to Jacob's request for tests. |
Good then I understood it correctly. I didn't think you didn't like the approach of this PR. I agree that tests are important. The reason why I haven't worked more on this PR is that I have other projects going on so I didn't get to it. It is on my TODO list. It doesn't help that the weather is really good now and I go outside in my free time 😆 . |
I'm pretty sure this approach won't work. There are several situations where weak dependencies are included through mechanisms that don't directly enable those features (like the user didn't specify the feature, or things like deferred features and such). I think the only option to minimize the entries in the resolve is to include all of the logic from the feature resolver in the dependency resolver, and we avoided that due to the level of complexity needed. |
The Cargo.lock generating resolver enables all features that a crate has. If that enables any features of dependencies, those are also enabled. This will also enable the weak dependencies. This PR changes nothing about that. However, the weak dependencies of dependencies are only enabled if that feature is. That's precisely what the two present tests test for:
WDYM by that? I grepped the cargo sources for that, the only place I could find was deferred profiles, which was something about debuginfo, and the |
Since the dependency resolver doesn't know about Deferred features is indeed related to the implementation of the feature resolver. When it sees the |
TODO better commit msg
850fb43
to
df83bae
Compare
I still don't understand your first paragraph. Would it be possible to give an example? I now see what you mean in your second paragraph about |
FWIW, if we want to bump the lockfile version, I have a list of what could be bumped together. |
df83bae
to
4f2d1b0
Compare
Here's an example: [package]
name = "z73"
version = "0.1.0"
edition = "2021"
[dependencies]
serde = {version = "1", optional = true }
[features]
foo = ["dep:serde"]
bar = ["serde?/derive"] |
@ehuss thanks, that looks like the Edit: pushed now, |
☔ The latest upstream changes (presumably #12279) made this pull request unmergeable. Please resolve the merge conflicts. |
@ehuss do you see any path forward here? It's important to me that my |
The blocker is the unification support (see the failing test), which also is kinda important. I need to have a closer look but right now I don't even know if this PR's approach is viable at all. An alternative to this PR might be to use the "features"/new resolver with some different parameters (to make it similar to the "dependencies"/old resolver). |
Unfortunately I don't see a path forward here. The current design was intentionally chosen to manage the complexity of the implementation. It might be possible to do post-resolution filtering, but that would require running feature resolution twice which could have a noticeable performance hit. |
Should this PR be closed then @ehuss? |
Yeah I think I will close this, even though I really want the feature. I don't have the time right now to fix the issues. Others are invited to work on this. Maybe in the future the approach could be tried out that we run feature resolution twice. It might have a performance impact, yes, but it will also create more correct output. Of course, if the existing dependency resolver could be made aware, that would be even better, but I'm not sure it is possible. Anyone, feel free to take my PR and make it work. |
@ehuss So if I am understanding this correctly. In order to fix the bug, we would need to unify both resolvers to use the same logic? Do we have an idea of the scope of the work and if so would it be possible to provide some pointers. I would be willing to help, but I have no idea where I would start. I am trying to see if there is a path forward for this issue that lingers and is becoming more problematic as many libraries are adopting the optional dependencies. |
@Sytten The resolvers were not unified on purpose. The complexity of doing whole graph optimization like the The So I would start by:
The easiest way to implement step 7 may be to adopt some wrapper around the pubgrub-rs library. I am busy working on that library to make it production ready for this purpose. I believe the lowering from cargo's understanding of dependency resolution to pubgrub's will automatically require/involve step 4, and should make at least "week" features not too complicated. I would happily support someone who wants to contribute by working on 1 - 6 while I continue to work on pubgrub! P.S. @epage: having written this to do list up, is there a more appropriate place for it to be recorded? |
@Eh2406 This is a really good starter thanks for that. I am going to try to tackle the first point this week. I have goos experience in rust but never contributed to cargo so I will likely need to have some reviews along the way. Is it ok if I tag you in draft PR? |
@Sytten Absolutely! Also we have Office Hours if you want to chat synchronously. This week schedules may be odd for the US holidays, so ping us on the zulip thread for the slot you want to attend. The |
doc: Add README for resolver-tests ### What does this PR try to resolve? This collect the comments from `@Eh2406` about the resolver-tests and add a README to it. ### How should we test and review this PR? ### Additional information Maybe Fixed #13319 See #11938 (comment)
doc: Add README for resolver-tests ### What does this PR try to resolve? This collect the comments from `@Eh2406` about the resolver-tests and add a README to it. ### How should we test and review this PR? ### Additional information Maybe Fixed #13319 See #11938 (comment)
doc: Add README for resolver-tests ### What does this PR try to resolve? This collect the comments from `@Eh2406` about the resolver-tests and add a README to it. ### How should we test and review this PR? ### Additional information Maybe Fixed #13319 See #11938 (comment)
test: add support for features in the sat resolver ### What does this PR try to resolve? This PR implements the first step of #11938 (comment). ### How should we test and review this PR? The first commit does some refactorings, and the second commit updates the SAT resolver. List of boolean variables in the SAT resolver: * One variable representing the activation of each registry package. * One variable representing the activation of each feature of a given registry package. * In the `sat_resolve()` method, we create an additional representing the activation of the root package. List of clauses in the SAT resolver: * If a package feature is activated, then the package should be activated. * No two packages with the same links set. * No two semver compatible versions of the same package. * For each package: - For each feature: - If the package feature is activated and it depends of another feature of the same package, then it is also activated. - If the package feature is activated and it depends of a dependency, then at least one of the compatible dependency package should be activated. - If the package feature is activated and it depends of a feature of a dependency, then the feature of a compatible dependency package should be activated only if the compatible dependency package is activated. If this is not a weak dependency feature, then at least one of the compatible dependency package should be activated. - For each dependency, if the package is activated and if the dependency is non-optional or has been activated, then at least one of the compatible dependency package and its required features should be activated. * The root package has the same dependency clauses but has no features. List of assumptions in the SAT resolver: * The root package is activated. * Old root packages from previous calls to `sat_resolve()` are deactivated. This is necessary since the proptest call `sat_resolve()` several times with a different root package using the same SAT resolver, and clauses relative to the root package are not removable.
I would like to assist in this effort, is there any timeline/current state I could get started from and try and contribute as well? |
In #10801, it was noted that Cargo treats weak dependencies just like strong ones in Cargo.lock, as in, includes them unconditionally. Cargo does not build these dependencies though, only uses them during resolution.
Cargo has two resolvers:
The implementation in #8818 only changed the latter resolver, which implemented weak dependency support for most important workflows, like determining which crates are actually built. The former resolver still keeps a list of enabled and disabled features for each crate, and the way more aggressive unification it performs isn't an issue for weak dependency support, so fundamentally one can add weak dependency support to it, too. This PR does that precisely:
ResolveVersion::V4
variant, which isn't emitted by default. The idea is though that at some point in the future cargo switches to the new version by default. I'm open to feedback for different suggestions how to phase in the change, maybe viaresolver = 3
, or maybe additionally by having an unstable flag so that we can iterate before version 4 is stabilized.Fixes #10801