Skip to content
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

Select pre-releases like pip does #141

Merged
merged 2 commits into from
Jan 25, 2024
Merged

Conversation

wolfv
Copy link
Member

@wolfv wolfv commented Jan 11, 2024

I tried something slightly different here: matching pre-releases but being able to pass in additional options to the contains(...) function.

I was planning to add a HashMap<PackageId, bool> that would contain wether a given package only has pre-releases, however, we don't have the pacakge names available. However, now that I am thinking of it, we could just add it as a second field to each version spec. Or maybe we should just add the prerelease yes/no option to the version spec itself. Maybe we don't even need the extra options ...

@baszalmstra
Copy link
Contributor

This seems rather complex. Why not store whether prerelase are supported in the version instead of in the versionset. You know all the information when all versions are constructed.

@wolfv
Copy link
Member Author

wolfv commented Jan 11, 2024

Hmm, maybe a good idea. We still need to store wether the versionset refers to any prerelease if I am not mistaken.

  1. When creating the versionset, we check if any element refers to a prerelease, and if yes, we store that as a bool (then we get rid of the iter().any() in the contains call
  2. When creating the version(s), we check if all of them are pre-releases, and store that as a bool in each version
  3. we could still have the global option as option that we pass to contains.

Does that make sense @tdejager @baszalmstra ? :)

@baszalmstra
Copy link
Contributor

I think we just need one boolean in the version and one in the versionset. Both define wether prereleases are allowed.

your 1 and 2 should be able to inform initial values there I guess!

I think the options can stay in the provider and be read to compute the booleans. I dont think we need to complicate resolvo.

@wolfv
Copy link
Member Author

wolfv commented Jan 11, 2024

Yep, you might be right :) I think what I just pushed captures your idea (I can revert back to stock-resolvo with this).

I did this pretty quickly – I think the code can be made more beautiful :)

@baszalmstra
Copy link
Contributor

Nice! Code could use some improvement indeed but I think the idea is solid!

@tdejager
Copy link
Contributor

Implementation looks solid!

Note that with this PR we are still deviating from the spec (https://packaging.python.org/en/latest/specifications/version-specifiers/#handling-of-pre-releases) if I'm reading it correctly namely.

https://packaging.python.org/en/latest/specifications/version-specifiers/#handling-of-pre-releases

... accept remotely available pre-releases for version specifiers where there is no final or post release that satisfies the version specifier

So instead matching pre-releases, only if the project has pre-releases, the spec said we should match if these are the only options that match this version range. However, as Bas and others noted, this is a bit of strange requirement that can potentially lead to unwanted behavior. Also, in issue #118 another issue followed that they want to investigate the spec and pip implementation anyways. pypa/pip#12471 (comment)

So I think it's fine at this point to deviate from spec, however, it should be noted in the code that we are doing so I think

@wolfv wolfv changed the title Different way of dealing with pre-releases Select pre-releases like pip does Jan 16, 2024
@wolfv
Copy link
Member Author

wolfv commented Jan 16, 2024

Added some docs, but no test yet. :)

Cargo.toml Outdated Show resolved Hide resolved
pub(crate) struct PypiVersionSet(Option<VersionOrUrl>);
pub(crate) struct PypiVersionSet {
spec: Option<VersionOrUrl>,
allows_prerelease: bool,
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It would be good to add a little bit of documentation to this field.

},
) => {
spec.contains(version)
&& (self.allows_prerelease || *only_prerelease || !version.any_prerelease())
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I have to try really hard to understand this boolean logic. Would you be able to comment it a little?

@wolfv wolfv linked an issue Jan 17, 2024 that may be closed by this pull request
@notatallshaw
Copy link

FYI, I've been testing this branch against the new apache-airflow, including the new 2.8.1 as they have completely revamped their packaging infrastructure: https://airflow.apache.org/docs/apache-airflow/stable/release_notes.html#airflow-packaging-specification-follows-modern-python-packaging-standards-36537

The pre-releases look good, but I think this exposes some other issues with what packages rip visits when resolving, I will retest and file new issues once this lands (as I am not able to merge this branch with main locally myself).

@wolfv wolfv force-pushed the prerelease-ii branch 2 times, most recently from e2123ab to 3b1f98b Compare January 23, 2024 16:17
Comment on lines 72 to 75
/// This is true if there are only pre-releases available for this package
/// For example, if the package `foo` has only versions `foo-1.0.0a1` and `foo-1.0.0a2`
/// then this will be true. This allows us later to match against this version and
/// allow the selection of pre-releases.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Comment needs to be updated to account for all cases that this can be set to true :)

@tdejager
Copy link
Contributor

Let's merge when we have fixed the open comments :)

@tdejager tdejager merged commit 11f6417 into prefix-dev:main Jan 25, 2024
5 checks passed
@wolfv wolfv deleted the prerelease-ii branch January 25, 2024 17:03
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

rip does not follow spec for handling of pre-releases
4 participants