我正在建立一个查询,以“宽”格式(长为CSV)返回高/窄表。
我提出的查询如下:
SELECT
CONV(a.assetID, 10, 16) AS assetID,
a.notes,
a.budgetReplaceDate,
p.propertyName AS property,
b.buildingName AS building,
MAX(IF(ad.fieldID = ?, ad.text, NULL)) AS ?,
MAX(IF(ad.fieldID = ?, ad.text, NULL)) AS ?,
MAX(IF(ad.fieldID = ?, ad.text, NULL)) AS ?,
MAX(IF(ad.fieldID = ?, ad.text, NULL)) AS ?,
MAX(IF(ad.fieldID = ?, c.choice, NULL)) AS ?,
MAX(IF(ad.fieldID = ?, ad.text, NULL)) AS ?
FROM
asset_details AS ad
INNER JOIN assets AS a ON a.assetID = ad.assetID
LEFT JOIN asset_choices AS c ON c.choiceID = ad.choiceID
LEFT JOIN property AS p ON a.propertyID = p.propertyID
LEFT JOIN property_buildings AS b ON a.buildingID = b.buildingID
WHERE
a.clientID IN(?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)
AND a.formID = ?
AND (
a.deletedID IS NULL
OR a.deletedID = 0
)
GROUP BY
assetID
ORDER BY
assetID
LIMIT
10 OFFSET 0
我要输入的参数如下:
array(29) {
[0]=> string(3) "385"
[1]=> string(4) "f385"
[2]=> string(3) "386"
[3]=> string(4) "f386"
[4]=> string(3) "387"
[5]=> string(4) "f387"
[6]=> string(3) "388"
[7]=> string(4) "f388"
[8]=> string(3) "389"
[9]=> string(4) "f389"
[10]=> string(3) "390"
[11]=> string(4) "f390"
[12]=> string(2) "14"
[13]=> string(2) "15"
[14]=> string(2) "26"
[15]=> string(2) "29"
[16]=> string(2) "30"
[17]=> string(2) "31"
[18]=> string(2) "32"
[19]=> string(2) "34"
[20]=> string(2) "35"
[21]=> string(2) "36"
[22]=> string(2) "37"
[23]=> string(2) "38"
[24]=> string(2) "39"
[25]=> string(2) "40"
[26]=> string(2) "41"
[27]=> string(2) "42"
[28]=> string(2) "41"
}
当尝试通过PHP中的PDO执行它时,出现以下错误:
警告:PDOStatement :: execute():SQLSTATE [42000]:语法错误或访问冲突:1064您的SQL语法有错误;您可能会发现错误。在网上的report.php的第1行中,检查与您的MySQL服务器版本相对应的手册以获取正确的语法,以在'SELECT CONV(a.assetID,10,16)AS assetID,a.notes,a.budgetReplaceDate,'附近使用580
如果我去手动将数组中的每个值复制并粘贴到查询中的正确位置,然后通过phpMyAdmin(或adminer)运行它,则它将正常工作。
我认为可能是这部分:
MAX(IF(ad.fieldID = ?, ad.text, NULL)) AS ?,
MAX(IF(ad.fieldID = ?, ad.text, NULL)) AS ?,
MAX(IF(ad.fieldID = ?, ad.text, NULL)) AS ?,
MAX(IF(ad.fieldID = ?, ad.text, NULL)) AS ?,
MAX(IF(ad.fieldID = ?, c.choice, NULL)) AS ?,
MAX(IF(ad.fieldID = ?, ad.text, NULL)) AS ?
,但是有一个简化的查询版本就可以了。我一生无法弄清楚发生了什么。我想念什么?
下面是常规日志:
Tcp port: 3306 Unix socket: /var/run/mysqld/mysqld.sock
Time Id Command Argument
2019-04-11T08:54:26.499114Z 376072 Connect *USERNAME*@localhost on *DATABASE* using TCP/IP
2019-04-11T08:54:26.499374Z 376072 Query SELECT sessionID, uid, loginDate, lastActive, ipAddress FROM session WHERE loggedOut = 0 AND token = '*REDACTED*' AND lastActive >= '2019-04-10 15:54:26' - INTERVAL 27 HOUR
2019-04-11T08:54:26.499889Z 376073 Connect *USERNAME*@localhost on *DATABASE* using TCP/IP
2019-04-11T08:54:26.500007Z 376073 Query SELECT userID, userEmail, userLevel, userGroupID, joinDate, firstname, lastname, subscriptionEndDate, contactNo, contractorID, homePropertyID, timezone, uuid FROM users WHERE userID = '2'
2019-04-11T08:54:26.500487Z 376074 Connect *USERNAME*@localhost on *DATABASE* using TCP/IP
2019-04-11T08:54:26.500595Z 376074 Query SELECT * FROM userGroups WHERE userGroupID = '1'
2019-04-11T08:54:26.500891Z 376073 Query SELECT ClientID FROM client
2019-04-11T08:54:26.501095Z 376073 Quit
2019-04-11T08:54:26.501180Z 376072 Query UPDATE session SET lastActive = '2019-04-11 18:54:26', browser = NULL WHERE sessionID = '2691'
2019-04-11T08:54:26.503173Z 376074 Query SELECT * FROM markers
2019-04-11T08:54:26.503416Z 376072 Quit
2019-04-11T08:54:26.503954Z 376074 Query SELECT f.formID, f.formName, f.formTable, f.category, f.budget, s.formName AS srvcName, s.formID AS srvcFormID, s.formTable AS srvcTable, s.srvcFreq AS freq FROM forms as f
LEFT JOIN srvcForms AS s ON f.formID = s.assetTable WHERE f.formID = '41' LIMIT 1
2019-04-11T08:54:26.504237Z 376074 Query SELECT * FROM formField WHERE formID = '41' ORDER BY position, fieldID
2019-04-11T08:54:26.504948Z 376074 Query SELECT
CONV(a.assetID, 10, 16) AS assetID,
a.notes,
a.budgetReplaceDate,
p.propertyName AS property,
b.buildingName AS building
,
MAX(IF(ad.fieldID = '385', ad.text, NULL)) AS 'f385',
MAX(IF(ad.fieldID = '386', ad.text, NULL)) AS 'f386',
MAX(IF(ad.fieldID = '387', ad.text, NULL)) AS 'f387',
MAX(IF(ad.fieldID = '388', ad.text, NULL)) AS 'f388',
MAX(IF(ad.fieldID = '389', c.choice, NULL)) AS 'f389',
MAX(IF(ad.fieldID = '390', ad.text, NULL)) AS 'f390'
FROM asset_details AS ad
INNER JOIN assets AS a ON a.assetID = ad.assetID
LEFT JOIN asset_choices AS c ON c.choiceID = ad.choiceID
LEFT JOIN property AS p ON a.propertyID = p.propertyID
LEFT JOIN property_buildings AS b ON a.buildingID = b.buildingID
WHERE a.clientID IN('14', '15', '26', '29', '30', '31', '32', '34', '35', '36', '37', '38', '39', '40', '41', '42') AND a.formID = '41' AND (a.deletedID IS NULL OR a.deletedID = 0)
GROUP BY assetID ORDER BY assetID LIMIT 10 OFFSET 0
2019-04-11T08:54:26.512918Z 376074 Quit
2019-04-11T08:54:32.938734Z 376067 Query set global general_log = "OFF"
答案 0 :(得分:1)
您不能使用?
占位符来指定MySQL准备语句中列的别名。因此,您应该只使用硬编码的别名:
SELECT
CONV(a.assetID, 10, 16) AS assetID,
a.notes,
a.budgetReplaceDate,
p.propertyName AS property,
b.buildingName AS building,
MAX(IF(ad.fieldID = ?, ad.text, NULL)) AS max_one,
MAX(IF(ad.fieldID = ?, ad.text, NULL)) AS max_two,
MAX(IF(ad.fieldID = ?, ad.text, NULL)) AS max_three,
MAX(IF(ad.fieldID = ?, ad.text, NULL)) AS max_four,
MAX(IF(ad.fieldID = ?, c.choice, NULL)) AS max_five,
MAX(IF(ad.fieldID = ?, ad.text, NULL)) AS max_six
FROM asset_details AS ad
-- the rest of your query the same
但是,我认为没有充分的理由来控制别名。您的PHP脚本可能还需要一个硬编码的已知别名才能提取该值。
答案 1 :(得分:0)
结果证明它确实在工作,这是一个进一步的错误。
我正在重写一个现有函数,但是没有注意到该函数进一步重复使用SQL查询来执行总记录数(以显示“查看1-10,共1000个结果”)。该错误实际上就是此错误,并且可以快速轻松地解决。
经验教训,请实际检查错误所在的行号!
说句公道话,我确实有一些错别字,只是没有注意到行号何时更改。