Yii2 查询未正确引用
Yii2 Query not quoting correctly
我运行陷入这个问题,一次又一次。很高兴找出如何正确构建查询,这样我就可以停止使用 Yii::$app->db->createCommand() 作为解决方法。
我的 Yii2 查询:
$users = UserSpatial::find()
->select('user_id, harvesine(y(coordinates), x(coordinates), :lat, :lon) as dist, astext(coordinates)')
->where('st_within(coordinates, envelope(linestring(point(:rlon1, :rlat1), point(:rlon2, :rlat2))))')
->orderBy('st_distance(point(:lon, :lat), coordinates)')
->params([
':lon' => $geo->lon,
':lat' => $geo->lat,
':rlon1' => $rlon1,
':rlat1' => $rlat1,
':rlon2' => $rlon2,
':rlat2' => $rlat2
])
->all();
生成的查询在所有错误的地方都带有反引号,奇怪的是,并非所有参数都被反引号(抱歉,但您需要仔细查看错位的反引号,因为我不知道如何最好地突出显示不正确的位置):
SELECT \`user_id\`, harvesine(y(coordinates), x(coordinates), \`32.7699547\`, \`-116.9911288)\` AS \`dist\`, astext(coordinates)
FROM \`user_spatial\`
WHERE st_within(coordinates, envelope(linestring(point(-117.07730792871, 32.697490931884), point(-116.90494967129, 32.842418468116))))
ORDER BY st_distance(point(-116.9911288, \`32.7699547)\`, \`coordinates)\`
查询应如下所示,因为我没有用双方括号括住任何字段或值:
SELECT \`user_id\`, harvesine(y(coordinates), x(coordinates), 32.7699547, -116.9911288) AS dist, astext(coordinates)
FROM \`user_spatial\`
WHERE st_within(coordinates, envelope(linestring(point(-117.07730792871, 32.697490931884), point(-116.90494967129, 32.842418468116))))
ORDER BY st_distance(point(-116.9911288, 32.7699547), coordinates)
我可以接受 Yii2 在字段名称和 table 名称周围添加一些反引号,但到底为什么要反引号呢? (仅供参考:$rlon 和 $rlat 值似乎没有反引号,但我假设这是因为它们是数学计算的结果!?!?)。
我已经尝试过强制 $geo->lon 和 $geo->lat 像这样浮动值:
'lon' => (float)$geo->lon;
或
'lon' => (float)$geo->lon * 1;
但没有用。
尝试对 select
和 orderBy
方法使用数组格式,例如 docs suggest:
Besides column names, you can also select DB expressions. You must use
the array format when selecting a DB expression that contains commas
to avoid incorrect automatic name quoting. For example,
$query->select(["CONCAT(first_name, ' ', last_name) AS full_name",
'email']);
你的情况是这样的:
$users = UserSpatial::find()
->select([
'user_id',
'harvesine(y(coordinates), x(coordinates), :lat, :lon) as dist',
'astext(coordinates)'
])
->where('st_within(coordinates, envelope(linestring(point(:rlon1, :rlat1), point(:rlon2, :rlat2))))')
->orderBy(['st_distance(point(:lon, :lat)', 'coordinates)'])
->params([
':lon' => $geo->lon,
':lat' => $geo->lat,
':rlon1' => $rlon1,
':rlat1' => $rlat1,
':rlon2' => $rlon2,
':rlat2' => $rlat2
])
->all();
我运行陷入这个问题,一次又一次。很高兴找出如何正确构建查询,这样我就可以停止使用 Yii::$app->db->createCommand() 作为解决方法。
我的 Yii2 查询:
$users = UserSpatial::find()
->select('user_id, harvesine(y(coordinates), x(coordinates), :lat, :lon) as dist, astext(coordinates)')
->where('st_within(coordinates, envelope(linestring(point(:rlon1, :rlat1), point(:rlon2, :rlat2))))')
->orderBy('st_distance(point(:lon, :lat), coordinates)')
->params([
':lon' => $geo->lon,
':lat' => $geo->lat,
':rlon1' => $rlon1,
':rlat1' => $rlat1,
':rlon2' => $rlon2,
':rlat2' => $rlat2
])
->all();
生成的查询在所有错误的地方都带有反引号,奇怪的是,并非所有参数都被反引号(抱歉,但您需要仔细查看错位的反引号,因为我不知道如何最好地突出显示不正确的位置):
SELECT \`user_id\`, harvesine(y(coordinates), x(coordinates), \`32.7699547\`, \`-116.9911288)\` AS \`dist\`, astext(coordinates)
FROM \`user_spatial\`
WHERE st_within(coordinates, envelope(linestring(point(-117.07730792871, 32.697490931884), point(-116.90494967129, 32.842418468116))))
ORDER BY st_distance(point(-116.9911288, \`32.7699547)\`, \`coordinates)\`
查询应如下所示,因为我没有用双方括号括住任何字段或值:
SELECT \`user_id\`, harvesine(y(coordinates), x(coordinates), 32.7699547, -116.9911288) AS dist, astext(coordinates)
FROM \`user_spatial\`
WHERE st_within(coordinates, envelope(linestring(point(-117.07730792871, 32.697490931884), point(-116.90494967129, 32.842418468116))))
ORDER BY st_distance(point(-116.9911288, 32.7699547), coordinates)
我可以接受 Yii2 在字段名称和 table 名称周围添加一些反引号,但到底为什么要反引号呢? (仅供参考:$rlon 和 $rlat 值似乎没有反引号,但我假设这是因为它们是数学计算的结果!?!?)。
我已经尝试过强制 $geo->lon 和 $geo->lat 像这样浮动值:
'lon' => (float)$geo->lon;
或
'lon' => (float)$geo->lon * 1;
但没有用。
尝试对 select
和 orderBy
方法使用数组格式,例如 docs suggest:
Besides column names, you can also select DB expressions. You must use the array format when selecting a DB expression that contains commas to avoid incorrect automatic name quoting. For example,
$query->select(["CONCAT(first_name, ' ', last_name) AS full_name", 'email']);
你的情况是这样的:
$users = UserSpatial::find()
->select([
'user_id',
'harvesine(y(coordinates), x(coordinates), :lat, :lon) as dist',
'astext(coordinates)'
])
->where('st_within(coordinates, envelope(linestring(point(:rlon1, :rlat1), point(:rlon2, :rlat2))))')
->orderBy(['st_distance(point(:lon, :lat)', 'coordinates)'])
->params([
':lon' => $geo->lon,
':lat' => $geo->lat,
':rlon1' => $rlon1,
':rlat1' => $rlat1,
':rlon2' => $rlon2,
':rlat2' => $rlat2
])
->all();