-
-
Notifications
You must be signed in to change notification settings - Fork 2.7k
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
Always use, and improve the AlwaysDispatchPrettyPrinter for diffs #11537
Always use, and improve the AlwaysDispatchPrettyPrinter for diffs #11537
Conversation
9e71d6a
to
7d4eec8
Compare
6eeef45
to
6ab988c
Compare
The normal default pretty printer is not great when objects are nested and it can get hard to read the diff. Instead, provide a pretty printer that behaves more like when json get indented, which allows for smaller, more meaningful differences, at the expense of a slightly longer diff
6ab988c
to
ce16d20
Compare
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.
Thanks @BenjaminSchubert, it'd be great to improve the diffs.
The pprint code is a bit hard to get into, before I/we do it, I think it would be helpful to show before/after examples on some common cases that are changed, both short and long.
Regarding the private implementation details, I wonder if we will now be changing enough things such that not much is left from the upstream PrettyPrinter? In that case, we can just copy pprint.py wholesale to pytest. My copy has 671 lines so it's not huge.
Advantages:
- No risk of breakage due to using private stuff
- Consistency between all Python versions
- Can backport pprint functionality from new Python versions
- Maybe can simplify/customize the code more directly?
Disadvantages:
- Maintenance overhead
- Missing on upstream improvements (unless we continuously backport)
@bluetech Good questions!
I have now updated the description with a (collapsed) section to show some small examples for better representation. It is quite extensive to the point of becoming hard to read, but let me know if there is a need for more.
That works for me, do you prefer me to copy the code and continue extending it as I did now, or do the modifiications directly there to simplify? And is another PR/branch easier for comparison, or are you happy with me just updating this one? |
Thank you @BenjaminSchubert, you examples are exactly what I hoped for. I think it would be very good to get wider feedback on this, maybe even asking some of our users on the internet :) @nicoddemus @RonnyPfannschmidt @The-Compiler WDYT? See @BenjaminSchubert many before/after examples in the PR description (make sure to expand).
A separate PR against current main would be great; it will be useful regardless and hopefully (maybe?) make the changes here easier to review. |
I've only looked at the output changes, but I like those a lot! Seems to make the output much more readable IMHO, and thanks to the |
I agree the outcome is great!
I agree copying it is probably the way to go. 👍 My suggestion is to add it to the repository without any changes in its own commit, and later on add the necessary changes in separate commits: having a single commit with the clean copy helps us to later see exactly what has changed. |
Hey, just want to make sure if I was meant to do something more still before reviews or not (I don't need a review right now, just want to make sure you are not waiting on me :) ) |
@BenjaminSchubert don't worry, you do not need to do anything else, it is on our plate now, thanks! |
Overview
Note: An alternative implementation has been made at #11571, following feedback.
The normal default pretty printer is not great when objects are nested it can get hard to read the diffs produced.
Instead, provide a pretty printer that behaves more like when json get which allows for smaller, more meaningful differences, at the expense of a slightly longer diff.
Fix #1531
Alternatives/Potential improvements
This has the disadvantage that diffs are now longer, even for small changes (like
[1, 2] == [1, 3]
). We could potentially still keep the previous implementation for the case where the diff is the same length AND has a single line. This would take care of trivial cases. It would however make some diffs harder to read again, like[1, 2, 3] == [2, 3, 4]
, which would now show 3 differences.This is however not generalisable to deeply nested payloads.
Notes for maintainers
This needs to work a lot with private details of the pretty printer. There was already some of that happening, but this makes it much more tied to it. It would technically be possible to reimplement most of it without touching private methods, but that would require a lot of copying. this module has been quite stable over time so it might not be worth it.
The first commit contains the initial 'crude' implementation, which mostly copy pastes and adapts the code from the standard librarie's prettyprinter. The second commit (the !fixup) cleans up the interface and removes duplication.
The support for dataclasses and simplenamespaces is degraded before python 3.10 and 3.9 respectively. I believe we could backport the implementation, but not sure how important that is.
Examples
Basic
Generated using the following script
We get the following differences on small entries:
Full example
Taking the example from https://github.com/lukaszb/pytest-dictsdiff, as in the issue:
Previously:
Now: