-
-
Notifications
You must be signed in to change notification settings - Fork 421
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
"...but could have been retrieved as a query" false positives or misleading suggestions #2045
Comments
Why can't you just use |
That will have the same problem, it will return whether result contains any rows, but not whether it has more than 1 row. Assuming you mean this: $hasAtLeastTwoArticles = $user->articles()->limit(2)->exists() |
Chatgpt suggests using YourModel::skip(1)->exists(); |
Good point, that should work for the second example. |
The problem here is that you need sub-queries to properly scope the count/exists methods: $isInTop3 = User::query()
->whereIn('id', User::select('id')->orderByDesc('score')->limit(3))
->whereKey($userId)
->exists(); |
Yes. I know, and that's the point of this issue. Both solutions are not obvious, and the lint suggestion makes it seem like you can just skip the |
Well what do you think should be done then? I'm not sure how well we'd be able to detect that you're trying to skirt around not using a subquery and an error shouldn't be raised. I don't think it's as simple as just detecting if
The error message never says to just remove the If you find yourself repeating this pattern around your codebase then that could be a great candidate for a scope or Builder macro. You can always locally ignore that error or just disable the rule altogether if you like: parameters:
noUnnecessaryCollectionCall: false |
Hi, As you described the error is technically correct. So if you feel like it is a false positive, feel free to ignore the error. Rule itself can't detect each edge case. Thank you! |
Description
I regularly hit this error in cases involving limit clause. The error is pretty misleading and can be considered false positive (but it's debatable).
Laravel code where the issue was found
This reports
Another one is something like this.
This reports:
The suggestion is technically correct, but the solution is often convoluted. What's worse, though, is that the suggestion is misleading - if you do the naive transformation that the error seems to suggest, for example:
You'll get the wrong result, because Eloquent will generate
select count(*) from articles limit 2
, which counts all articles, but what you want isselect count(*) from (select id from articles limit 2) as first_two_articles
The correct solution is quite convoluted, because you have to make sure the Eloquent doesn't generate
count(*)
inside the subquery, which it often does (usingloadCount
orloadAggregate
) so it's usually simpler to pull all results and count them in PHP (especially when it's about small counts like the examples above).The text was updated successfully, but these errors were encountered: