Improper treatment of booleans in QueryBuilder::toRawSql for Postgres #48035
Replies: 5 comments 1 reply
-
Changing this in Laravel may break some applications. So it is not a good approach to change it. Casting those values to If you've had this problem or insist on having |
Beta Was this translation helpful? Give feedback.
-
@tpetry unfortunately, postgres does not seed to be able to cast When I try to replay manually an SQL query fetched from
Is it a configuration problem in postgres ? I quite don't understant why the int instead of bool will pass in PDO but not in the pgsql console. |
Beta Was this translation helpful? Give feedback.
-
I think maybe that was the edge case for me too, not quite sure. As said, you can use my |
Beta Was this translation helpful? Give feedback.
-
Ok. There is some black magic in PDO that I can't understand but boolean columns are sent as boolean to postgres, not integers. User::query()->where('is_admin', true)->where('id', 1)->get();
// postgres log :
// execute pdo_stmt_00000003: select * from ""users"" where ""is_admin"" = $1 and ""id"" = $2","parameters: $1 = 't', $2 = '1'
// toRawSql :
// select * from "users" where "is_admin" = 1 and "id" = 1
User::query()->where('is_admin', 1)->where('id', 1)->get();
// execute pdo_stmt_00000003: select * from ""users"" where ""is_admin"" = $1 and ""id"" = $2","parameters: $1 = 't', $2 = '1'
// select * from "users" where "is_admin" = 1 and "id" = 1
User::query()->where('is_admin', '1')->where('id', '1')->get();
// execute pdo_stmt_00000003: select * from ""users"" where ""is_admin"" = $1 and ""id"" = $2","parameters: $1 = 't', $2 = '1'
// select * from "users" where "is_admin" = '1' and "id" = '1'
User::query()->where('is_admin', 'true')->where('id', '1')->get();
// execute pdo_stmt_00000003: select * from ""users"" where ""is_admin"" = $1 and ""id"" = $2","parameters: $1 = 't', $2 = '1'
// select * from "users" where "is_admin" = 'true' and "id" = '1' It looks like the bindings are treated slightly differently between Eloquent -> PDO -> Database and Eloquent -> rawSql. In any case, great job on your recent contributions, it will help a lot ! |
Beta Was this translation helpful? Give feedback.
-
@tpetry - I have just run into this issue today, raw SQL dumps have the bool value as 1/0 - when I take the sql query dump and try to run it in TablePlus because of the native bool types, the query errors out. Will the package you mentioned fix the output for the toRawSql() Method for Postgres? |
Beta Was this translation helpful? Give feedback.
Uh oh!
There was an error while loading. Please reload this page.
Uh oh!
There was an error while loading. Please reload this page.
-
Laravel Version
10.17
PHP Version
8.2.8
Database Driver & Version
Postgresql 14
Description
When using Postgresql, booleans are transformed into integers in
Builder::toRawSql()
.I tried to fix it but I'm a bit worried to make a mess to fix that.
PostgresConnection
does have a validescapeBool
method but the proble is higher in the call stack.When running
User::query()->where('is_admin', true)->toRawSql();
,toRawSql()
looks likewhich resolves in
because of
framework/src/Illuminate/Database/Connection.php
Lines 713 to 729 in 19b4209
(note that the boolean cast into integer)
@tpetry Any smart idea to fix that ?
I guess overriding
prepareBindings
andbindValues
inPostgresConnection
should do the trick but is not a valid move for Laravel :Related explanations on why booleans are casted to integers in Laravel by Taylor : php/php-src#6801 (comment)
Steps To Reproduce
returns
'select * from "users" where "is_admin" = 1'
while it should return
'select * from "users" where "is_admin" = true'
Beta Was this translation helpful? Give feedback.
All reactions