mirror of
https://github.com/doctrine/orm.git
synced 2026-03-23 22:42:18 +01:00
Passing a single argument to the QueryBuilder::where() method using named arguments #7321
Reference in New Issue
Block a user
Delete Branch "%!s()"
Deleting a branch is permanent. Although the deleted branch may continue to exist for a short time before it actually gets removed, it CANNOT be undone in most cases. Continue?
Originally created by @deasraze on GitHub (Feb 13, 2024).
Bug Report
Summary
Hello there! When we try to call the
QueryBuilder::where()method using a named argument, we encounter an issue with accessing an undefined array key. As a result, we get a "Warning: Undefined array key 0". The problem occurs because the value of the argument is an associative array.9acc70d5b8/src/QueryBuilder.php (L954)Current behavior
Warning: Undefined array key 0
How to reproduce
Сall the
QueryBuilder::where()method using a named argument:Expected behavior
The method worked without errors.
@derrabus commented on GitHub (Feb 13, 2024):
You cannot target a variadic parameter with named arguments. That's a limitation of PHP and we can't do much about it.
The best we could do here is to throw if we detect unexpected named arguments in
$predicates. Not sure if it's worth it though.@deasraze commented on GitHub (Feb 13, 2024):
Sorry, but PHP doesn't prohibit the use of named arguments in conjunction with variadic parameter, as long as only one argument is passed at a time. Due to the fact that only one argument is being used, this piece of code is functioning properly.
3v4l example
Calling the
QueryBuilder::select()method work without errors when using$qb->select(select: 't.column').It seems to me that a possible solution in this situation would be to at least ban the use of named arguments with the
@no-named-argumentsor fix a bug that does not take this scenario into account.@derrabus commented on GitHub (Feb 13, 2024):
I didn't say that it prohibits it. I said, it doesn't support it.
It's not and you can see that in the output. You're not targeting the
$variadicparameter with the named argumentvariadic:. Instead, PHP passes all arguments (ordered or named) that it could not match to any parameter (which includes yourvariadic:argument) as an array to the variadic parameter. This becomes clearer if you add more arguments to the call:https://3v4l.org/LSYaK
So, your example code does something, but clearly not what you think it would.
Be my guest. 🙂
@deasraze commented on GitHub (Feb 13, 2024):
It seems that we misunderstood each other due to my poor English :(
From the PHP perspective, we can write
foo(variadic: 'some')but we cannot writefoo(variadic: 'some', variadic: 'other'). In the first case and based on your example, the code would be correct, as PHP would be able to execute it, but if we were to callwhere(predicates: 't.column= :value')orwhere(column: 't.column = :value'), we would fail because the code tries to access a non-existent key. It's not obvious.Thanks.
@derrabus commented on GitHub (Feb 13, 2024):
If a method has a variadic signature, you can (in addition to the mandatory parameters) pass any number of ordered or named arguments you like to that method. The question is, does it make sense semantically and what do you expect to happen when you do that? Just because you can, does it mean you should?
Your expectation was:
I'm disputing that because we never documented that we would expect arbitrary named arguments on this method. I understand that the error message is more of the garbage-in-garbage-out type and we can certainly improve that. But if we do, it will still be an error, that's for sure.
@derrabus commented on GitHub (Feb 13, 2024):
see #11260
@deasraze commented on GitHub (Feb 14, 2024):
This will really help improve the DX and help prevent possible problems if we are expecting to receive the value of an argument in the form of a
list<mixed>type. Thank you.