-
Couldn't load subscription status.
- Fork 1.2k
Avoid to open all documents from cursors in an if stmt #655
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
Conversation
Using a cursos in an if statement: cursor = Collection.objects if cursor: (...) Will open all documents, because there are not an __nonzero__ method. This change check only one document (if present) and returns True or False.
tests/queryset/queryset.py
Outdated
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.
I don't think this is correct. If the query set contains some data, it should be truthy regardless of the position of the cursor. Note that for obj in qs will always rewind the cursor and start from the beginning. It would be very weird to have something like produce output:
if not qs:
for obj in qs:
print obj
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.
Maybe, __nonzero__ can rewind the cursor. The main problem is performance. For example, if Test.objects is large (I tested a collection with 900k documents), a simple if cursor: will open all documents.
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 could work. An alternative would be to make use of objects.first() in __nonzero__. It would also be cool to clear the ordering on a query set (because you don't need the performance overhead of sorting if you're only interested in checking if a query set is non-empty).
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.
Yes, check first() appears to be better option than for loop with rewind. Changed.
|
Would be cool to add a test case that shows the performance increase. E.g. you could use Indeed, right now it fails on the master branch. How about some bonus points for clearing ordering? :) You'd have to check that calling |
|
I cloned queryset to clear _ordering list. So, test first() again |
|
Looks good - one last thing I'd check is if clearing and using |
|
Default ordering is treated on cursor_obj. Test added. |
|
You could make _bool a public method and change the name to has_data and docstring to "Retrieves whether cursor has any data". |
|
@jonathansp @tmpapageorgiou quoting The Zen of Python (
That being said, I personally dislike the ability to choose between As for the default ordering specified via |
|
@jonathansp clearing the default ordering needed a fix indeed. See #657. |
|
@wojcikstefan cool! I will change to: Do I need wait for your PR? |
|
@jonathansp you don't need to wait for my PR, although - combined with yours - it'll make things faster. |
|
Added PR #657 |
|
What do you think about ? |
|
I think it's fine now, but I don't have the power to merge it :) |
|
Good job @jonathansp and @wojcikstefan ! Merge! |
Avoid to open all documents from cursors in an if stmt
Using a cursos in an if statement:
Will open all documents, because there are not an
__nonzero__method.This change check only one document (if present) and returns
TrueorFalse.