Skip to content

New Resolver Error Reporting (case: ward==0.44.1b0 and py2neo==4.3.0) #8220

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

Closed
nlhkabu opened this issue May 11, 2020 · 18 comments
Closed

New Resolver Error Reporting (case: ward==0.44.1b0 and py2neo==4.3.0) #8220

nlhkabu opened this issue May 11, 2020 · 18 comments
Labels
C: dependency resolution About choosing which dependencies to install type: bug A confirmed bug or unintended behavior UX User experience related

Comments

@nlhkabu
Copy link
Member

nlhkabu commented May 11, 2020

Packages ward and py2neo (as reported via the pip research survey)

Resolver will go all the way down to ward 0.28.0b0 (current version is 0.45.0b0) to resolve dependency conflicts.

With pinned versions, here is the output:

(pip-exp) [nlh@navi personal]$ pip --version
pip 20.1 from /home/nlh/.virtualenvs/pip-exp/lib/python3.7/site-packages/pip (python 3.7)
(pip-exp) [nlh@navi personal]$ pip install ward==0.44.1b0 py2neo==4.3.0 --unstable-feature=resolver
Collecting https://files.pythonhosted.org/packages/af/41/c2d52a226b560618fe3df213a15e3f1ea3da09b8520a439756b619f3157d/py2neo-4.3.0.tar.gz#sha256=a218ccb4b636e3850faa6b74ebad80f00600217172a57f745cf223d38a219222
  Using cached py2neo-4.3.0.tar.gz (71 kB)
Collecting https://files.pythonhosted.org/packages/0b/7e/ca368a8d8e288be1352d4e2df35da1e01f8aaffbf526695df71630bcb8a6/neotime-1.7.4.tar.gz#sha256=4e0477ba0f24e004de2fa79a3236de2bd941f20de0b5db8d976c52a86d7363eb (from py2neo==4.3.0)
  Using cached neotime-1.7.4.tar.gz (17 kB)
Collecting ward==0.44.1b0
  Using cached ward-0.44.1b0-py3-none-any.whl (28 kB)
Collecting https://files.pythonhosted.org/packages/5b/7c/7bc4b5d74fdf890dadf1ca1057e4ce83d2ae51e89e69aa603310d63c9b07/ward-0.44.1b0.tar.gz#sha256=074fca910d0be929f753575b4657d0b94e0e3da45902bce0e96f9db5ca1d16fb
  Using cached ward-0.44.1b0.tar.gz (27 kB)
  Installing build dependencies ... done
  Getting requirements to build wheel ... done
    Preparing wheel metadata ... done
ERROR: Could not find a version that satisfies the requirement pygments~=2.3.1 (from py2neo)
ERROR: Could not find a version that satisfies the requirement pygments<3.0.0,>=2.4.2 (from ward)
ERROR: Could not find a version that satisfies the requirement pygments~=2.3.1 (from py2neo)
ERROR: Could not find a version that satisfies the requirement pygments<3.0.0,>=2.4.2 (from ward)
ERROR: No matching distribution found for pygments, pygments, pygments, pygments
@ghost ghost added the S: needs triage Issues/PRs that need to be triaged label May 11, 2020
@pradyunsg pradyunsg added C: dependency resolution About choosing which dependencies to install C: new resolver state: needs eyes Needs a maintainer/triager to take a closer look type: bug A confirmed bug or unintended behavior labels May 12, 2020
@ghost ghost removed the S: needs triage Issues/PRs that need to be triaged label May 12, 2020
@pfmoore
Copy link
Member

pfmoore commented May 28, 2020

Slightly different output with the latest version of the resolver (20.2b1):

>pip install ward==0.44.1b0 py2neo==4.3.0 --unstable-feature=resolver
Collecting ward==0.44.1b0
  Downloading ward-0.44.1b0-py3-none-any.whl (28 kB)
Collecting py2neo==4.3.0
  Downloading py2neo-4.3.0.tar.gz (71 kB)
     |████████████████████████████████| 71 kB 4.8 MB/s
ERROR: Could not find a version that satisfies the requirement pygments<3.0.0,>=2.4.2 (from ward)
ERROR: Could not find a version that satisfies the requirement pygments~=2.3.1 (from py2neo)
ERROR: No matching distribution found for pygments, pygments

What would you like to see in the way of an error that would help diagnose?

(I also tried using -v, and the output was many pages of detail, that I don't think is too helpful, so I would not recommend -v in this case!)

@ei8fdb
Copy link
Contributor

ei8fdb commented May 28, 2020

(This install is documented on a gist)

@nlhkabu @pfmoore

Current error message

ERROR: Could not find a version that satisfies the requirement pygments<3.0.0,>=2.4.2 (from ward)
ERROR: Could not find a version that satisfies the requirement pygments~=2.3.1 (from py2neo)
ERROR: No matching distribution found for pygments, pygments

Verbose explanation

NB: this is just for documentation to make sure I understand the situation correctly.

I can't install the combination of ward v0.44.1b0 and py2neo 4.3.0 because:

  1. ward needs a version of pygments lower than 3.0.0 but greater or equal to 2.4.2, and
  2. py2neo needs a version of pygments approximately equal to version 2.3.1

Before you read the error message

The main decision we need to make first is - what format the error message should take.

We are proposing 3 parts to an error message - each of these parts are based on established good user-centred design practice for error messages.

Part 1 What is the error

Give explicit indication of what has gone wrong - precise descriptions of exact problems, rather than vague generalities.

Part 2 - what has caused the error

Provide an explanation about what has caused pip to display this error.

Part 3 - possible ways to solve the error

Provide the user with constructive advice on how to fix the problem.

Proposed error message

So, onto our proposed message for this example. I have included the 3 parts as mentioned above.

pip install ward==0.46.0-beta.0 py2neo==4.3.0

(Part 1 What is the error?)
Cannot install ward v0.44.1b0 and py2neo v4.3.0 because these package versions have conflicting dependencies.

(Part 2 - what has caused the error)
The conflict is caused by:

  • ward 0.44.1b0 depends on pygments <3.0.0,>=2.4.2 (lower than 3.0.0 but greater or equal to 2.4.2)
  • py2neo 4.3.0 depends on pygments ~=2.3.1 (approximately equal to version 2.3.1)

(Part 3 - possible ways to solve the error)
There are a number of possible solutions. You can try:

  1. removing package versions from your requirements, and letting pip try to resolve the problem for you
  2. trying a version of ward that depends on pygments v2.3.1. Try pip-search ward --dep pygments~=2.3.1
  3. replacing ward or py2neo with a different package altogether
  4. patching py2neo to use pygments <3.0.0,>=2.4.2
  5. force installing (Be aware!)

For instructions on how to do these steps visit: https://pypa.io/SomeLink"
To debug this further you can run pip-tree to see all of your dependencies.

@pfmoore
Copy link
Member

pfmoore commented May 28, 2020

Minor point: ~= is Compatible version. It's relevant here because there's context that we have to assume the user understands, about how versions are specified.

So to be 100% explicit, you are proposing that the user should see the following:

>pip install ward==0.44.1b0 py2neo==4.3.0 --unstable-feature=resolver
Collecting ward==0.44.1b0
  Downloading ward-0.44.1b0-py3-none-any.whl (28 kB)
Collecting py2neo==4.3.0
  Downloading py2neo-4.3.0.tar.gz (71 kB)
     |████████████████████████████████| 71 kB 4.8 MB/s
ERROR: Cannot install ward v0.44.1b0 and py2neo v4.3.0 because these package versions have conflicting dependencies.
The conflict is caused by:
    ward 0.44.1b0 depends on pygments <3.0.0,>=2.4.2 (lower than 3.0.0 but greater or equal to 2.4.2)
    py2neo 4.3.0 depends on pygments ~=2.3.1 (approximately equal to version 2.3.1)

There are a number of possible solutions. You can try:
    removing package versions from your requirements, and letting pip try to resolve the problem for you
    trying a version of ward that depends on pygments v2.3.1. Try pip-search ward --dep pygments~=2.3.1
    replacing ward or py2neo with a different package altogether
    patching py2neo to use pygments <3.0.0,>=2.4.2
    force installing (Be aware!)

For instructions on how to do these steps visit: https://pypa.io/SomeLink"
To debug this further you can run pip-tree to see all of your dependencies.

That seems... rather verbose? It also has a number of practical issues in the "possible solutions" section.

  • How do we determine (from the information pip has) that the advice is reasonable? Or is this all just boilerplate that would be produced for every such error?
  • The pip-search tool mentioned doesn't exist (as far as I can see). We should stick to things that are actually available 🙂 I get that this is an example, but at some point we need to pin down the precise text, so I'm suggesting we do that now. Same for the link to the docs. And pip-tree.
  • Who is the "patching py2neo" advice aimed at? Most users would likely only be able to go as far as "file a bug report against py2neo and wait"...

In terms of implementability, the following issues need to be considered:

  1. The exact text to use, as noted above.
  2. There's no library or code we can use to convert a spec into "human readable" form. I'd suggest that adding human-readable versions be a possible future improvement, rather than something we need right now.
  3. We need to define what precisely would trigger this particular error - at the moment we do exactly the same for every occurrence of ResolutionImpossible, so if we want to be more specific, we need to understand what message applies in which case. I'd suggest that by default we have one message for all occurrences, and see if that works.

@pradyunsg pradyunsg changed the title Resolver error: ward and py2neo New Resolver Error Reporting (case: ward==0.44.1b0 and py2neo==4.3.0) Jun 1, 2020
@ei8fdb
Copy link
Contributor

ei8fdb commented Jun 2, 2020

That seems... rather verbose? It also has a number of practical issues in the "possible solutions" section.

Whats important is the structure of the message - 3 parts:

  1. what the error is (i.e. what the user has tried to do)
  2. what has caused the error
  3. possible ways to solve the error

I understand you and @pradyunsg are reluctant to provide 3., so l'm ok with testing only providing 1 and 2 with users and see the reaction.

How do we determine (from the information pip has) that the advice is reasonable? Or is this all just boilerplate that would be produced for every such error?

If all ResolutionImpossible error are created in the same way, then the error text is as you say boilerplate (better: consistent).

Same for the link to the docs.

The link to docs was discussed with @pradyunsg @nlhkabu as a way to provide the user with a possible ways to solve the error. The thinking was it is easier and quicker to update a pypa documentation link than roll-out a new version of pip.

Who is the "patching py2neo" advice aimed at? Most users would likely only be able to go as far as "file a bug report against py2neo and wait"...

This advice came from @pradyunsg, as a suggestion about how to solve this issue.

You raise a good point tho' - we've not suggested raising a ticket/bug against the packages the user was trying to install.

There's no library or code we can use to convert a spec into "human readable" form. I'd suggest that adding human-readable versions be a possible future improvement, rather than something we need right now.

I don't understand "use to convert a spec into "human readable" form". Can you explain this more? Will this have an impact on the error message?

We need to define what precisely would trigger this particular error - at the moment we do exactly the same for every occurrence of ResolutionImpossible
so if we want to be more specific, we need to understand what message applies in which case.
I'd suggest that by default we have one message for all occurrences, and see if that works.

As I mention above - if all occurences are triggered the same way then yes keep the message consistent. If not, do we know the other ways it's caused?

If not then I agree with, we should make this the message consistent for the moment.

(I'm going to open a ticket for ResolutionImpossible error message, as I've done for new resolver flag. I'll reference this.)

@pfmoore
Copy link
Member

pfmoore commented Jun 2, 2020

I don't understand "use to convert a spec into "human readable" form". Can you explain this more? Will this have an impact on the error message?

In <3.0.0,>=2.4.2 (lower than 3.0.0 but greater or equal to 2.4.2), the text <3.0.0,>=2.4.2 is directly available to pip from the project metadata. The text "(lower than 3.0.0 but greater or equal to 2.4.2)" is a translation of that into a more "friendly" form. But doing that translation would involve writing code for it, and that code doesn't exist yet.

In general, I'd say:

  1. Writing good code that translates all the possible forms of dependency data (see PEP 440 for how complex that is!) into natural language would be a pretty big exercise.
  2. I'd much rather see that handled in a library (maybe packaging, maybe something standalone) rather than being an implementation detail of pip. It's a classic example of something lots of people might want to do, and consistency of results is important.

So basically, we don't have a means of generating that parenthesised explanatory text at the moment, and it's a lot of work (I'd say at least multiple days, quite possibly weeks). Do you consider it important enough to warrant that amount of work? My problem is that as a developer, I tend to de-prioritise UI issues too much, so I automatically assume that "fix the obscure test cases so the test suite passes 100%" is more important than this. Hence why we need guidance here on where to invest effort...

@nlhkabu
Copy link
Member Author

nlhkabu commented Jun 2, 2020

@pfmoore Is there not a library that handles changing:
<3.0.0,>=2.4.2 into lower than 3.0.0 but greater or equal to 2.4.2 ?

@uranusjr
Copy link
Member

uranusjr commented Jun 2, 2020

There is not such a library as far as I know.

@nlhkabu
Copy link
Member Author

nlhkabu commented Jun 2, 2020

Ok, could we do this using a dict?
e.g.

human_readable_operators= {
    "<": "less than",
    "<=": "less than or equal to",
    ...
}

@nlhkabu
Copy link
Member Author

nlhkabu commented Jun 2, 2020

What is is about the project meta data that makes it more complex than this?

@uranusjr
Copy link
Member

uranusjr commented Jun 2, 2020

I guess? This will need to handle more complex cases, however, such as ==5.*, ~=21.0, etc. Here’s a rundown of possible specifiers: https://www.python.org/dev/peps/pep-0440/#version-specifiers

@nlhkabu
Copy link
Member Author

nlhkabu commented Jun 2, 2020

ok
@uranusjr @pfmoore would it be helpful if me and @ei8fdb provided you with a dict containing each of the specifiers listed in pep 440?

Maybe the way forward here is to cover the most common use cases, and just not output any human readable content for cases that are too complex?

@uranusjr
Copy link
Member

uranusjr commented Jun 2, 2020

I think that would be very helpful!

@pfmoore
Copy link
Member

pfmoore commented Jun 2, 2020

Note that this is addressing my concern that "it may be hard to do this", but I still believe it should be handled in packaging, (or another library) not in pip, where it cannot be reused by others. Not that making a PR against packaging is that much harder than making one against pip...

@nlhkabu
Copy link
Member Author

nlhkabu commented Jun 2, 2020

I agree @pfmoore - it would be ideal if other packaging projects could reuse this functionality, given it is not pip specific.
Could you open a ticket on the appropriate repository and ping me and @ei8fdb? We will add the dict there :)

@pfmoore
Copy link
Member

pfmoore commented Jun 2, 2020

pypa/packaging#312

@ei8fdb
Copy link
Contributor

ei8fdb commented Jun 2, 2020

@uranusjr https://www.python.org/dev/peps/pep-0440/#version-specifiers

Is this the complete list of possibilities?

@ei8fdb
Copy link
Contributor

ei8fdb commented Jun 11, 2020

@nlhkabu , @pfmoore @uranusjr @pradyunsg I think it's OK to close this ticket. Thoughts?

@pfmoore
Copy link
Member

pfmoore commented Jun 11, 2020

It basically seems like a duplicate of #8377, so yes, let's close this and focus on that one

@ei8fdb ei8fdb closed this as completed Jun 11, 2020
@github-actions github-actions bot locked as resolved and limited conversation to collaborators Oct 14, 2021
@pradyunsg pradyunsg removed the state: needs eyes Needs a maintainer/triager to take a closer look label Dec 9, 2022
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
C: dependency resolution About choosing which dependencies to install type: bug A confirmed bug or unintended behavior UX User experience related
Projects
None yet
Development

No branches or pull requests

5 participants