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
Amend RFC 1105 to specify how dependency versions relate to semver #1890
Conversation
This sentence is supposed to say "public dependency", right? |
@sgrif: I have a question about the notion of "superset" that determines whether you need to issue a major bump or not. In particular, I'm wondering whether upgrading a dependency from ^1.0.0 to ^1.0.5 is acceptable. The latter requirement is definitely not a superset of the former. But I am quite worried about such dependency upgrades causing major bumps, even if limited to public dependencies. If we're thinking specifically about the breakage such a dependency update could cause, I believe the main issue is that other crates in the graph could have an =1.0.0 dependency, so that moving to ^1.0.5 would create a conflict. Is that what you were thinking? As you're probably aware, there's long been an idea floating around to explicitly distinguish between public and private dependencies in Cargo.toml, together with tooling support (e.g. to check whether these declarations are correct, and such that any for any public dependencies that can come into contact, only one global version is allowed). If we moved to such a scheme, you could then imagine saying:
Does that make sense? |
No, I don't think so. There should (in theory) be no reason to need to make such a change though, is there?
Pretty much, yeah. I could definitely see the argument behind considering patch version bumps a minor change, but at the same time there's not really any reason in practice to specify a minimum patch version.
This removes the ability to write |
While going from 1.0.0 to 1.0.5 sounds weird indeed, there is a very legit need to sometimes bump a dependency from 1.0.0 to 1.1.0 and that seems forbidden as a minor bump in your new scheme of things. This doesn't sound like a good thing. How does anyone make us of new APIs in minor bumps of dependencies if that can only be a major bump in your own crate? |
Two clarifications:
-As @nox says, a minor bump of a public dependency is a very important use-case, and forcing a major bump in these cases would be a pretty heavy restriction. To elaborate a bit more: the way that a minor/patch-level bump can cause breakage is if downstream code also publicly depends on the same version of the bumped crate but explicitly disallows the minor bump. To formalize this, we can say that a version constraint is "semver open" if, for every version Some thoughts about these constraints:
Does that make sense to you? |
With current Cargo, going from |
@nox I think you misunderstood what I was getting at. Let me be more concrete. Suppose we have three crates:
My point is that if crate B revises its constraint to However, if crate C had said The difference is that the With that in hand, the proposal is that if we require all public dependency constraints to have this form -- to be "semver-open" -- then a minor/patch bump can't break the dependency graph (and should not break the ability to compile), and hence should be permitted without forcing a major bump in crate B's version. |
I'm in favor of restricting public dependencies to semver open with or without Cargo enforcement. I will update the PR when I have time. |
Oh right. But what about the case I mentioned though?
If crate C revises its constraint to Should that be considered as a Cargo bug, or as something that this RFC should limit? |
@nox I wouldn't consider that a Cargo bug per se. However, part of the idea of "public dependency" that's been floating around is that you'd explicitly say which of your dependencies are public, and which are private (and we could check that you're correct about this). Then Cargo would refuse to resolve a graph with multiple versions of a shared, public dependency. I'm not sure precisely what this would mean for All that said -- the full details of public vs private dependencies as an explicit notion in Cargo merits its own RFC, and that's something we should push toward in the near future. I'd expect that RFC to give a clearer answer to your question. |
Thanks for the RFC @sgrif! I think you, @aturon, and @nox have already articulated my primary concern with this RFC where I would consider a change from Some other comments from the RFC I've got are:
I don't quite follow this, right now
It may be worth specifying if it's possible to make a public dependency optional but still enabled by default. While this seems like it may be backwards compatible it may not always be. @nox the case you mentioned is accurately described by @aturon. It's not really a bug today but if Cargo had a distinction between public/private it'd definitely be a bug. |
Sorry, I originally wrote that as |
Ah makes sense! |
I really want to emphasize that we need to Cargo to a place where no dependency change is a breaking change. Otherwise, we end up in a situation where breaking changes always necessitate downstream to also make a breaking change if the new version is to be used, even if nothing downstream actually uses any part of the interface that broke. I consider this from a ecosystem/software-engineering perspective absolutely untenable. Unique version choices (made workable via public/private deps) will solve this, so I eagerly await that RFC. |
As an extension of this, it should be noted that it is impossible to update a | ||
dependency which contains a breaking change that affects your library, without | ||
making a breaking change yourself. As such, all libraries should follow Rust's | ||
example by committing to stability. Libraries which are stable (version is |
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.
A version greater than 1.0.0 doesn't mean the library is stable. You can still bump the major version as often as you want.
considers it to be so. | ||
|
||
As an extension of this, it should be noted that it is impossible to update a | ||
dependency which contains a breaking change that affects your library, without |
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.
That's not correct. Consider if you only use items of a crate publicly that were not broken. Then your users won't notice anything.
The libs team discussed this RFC a bit in our triage meeting. The consensus was that this seems like the right direction (modulo making updates based on the comment thread so far), but that it may be best to hold off on landing this policy until explicit public dependencies have landed in Cargo. @mitsuhiko is working on an RFC for that feature, and we're trying to line up some implementation help as well. On that basis, I'm going to go ahead and formally propose that we postpone, but feel free to push back! @rfcbot fcp postpone |
Team member @aturon has proposed to postpone this. The next step is review by the rest of the tagged teams: No concerns currently listed. Once these reviewers reach consensus, this will enter its final comment period. If you spot a major issue that hasn't been raised at any point in this process, please speak up! See this document for info about what commands tagged team members can give me. |
I'm in favor of postponing this if explicit public dependencies are in the near future. |
🔔 This is now entering its final comment period, as per the review above. 🔔 |
The final comment period is now complete. |
Closing now that FCP has elapsed (as postponed) |
Rendered