在 Go mySql 查询中对除 int 以外的任何内容使用占位符 ?



我已经设置并ping了我的mysql数据库连接。它正在工作,我可以使用两个数据库返回行。查询,并首先准备查询。我可以使用占位符来指定 ID。是否可以使用 ?作为列名的占位符?在这里的示例中,我尝试返回表personsfirstName列中的所有行。

qry, err := db.Prepare("SELECT ? FROM persons")
if err != nil { log.Fatal(err) }
defer qry.Close()
rows, err :=qry.Query("firstName")
if err != nil { log.Fatal(err) }
defer rows.Close()

我收到以下错误:错误 1064:SQL 语法有错误; 检查与您的MySQL服务器版本相对应的手册是否正确 在第 1 行的"?"附近使用的语法

不能将占位符用于标识符(例如表和列名称),占位符用于。你可以认为标识符类似于 Go 中的变量或函数名称,因此能够对标识符使用占位符类似于在各种脚本语言中具有eval

这减少了您在运行时之前不知道标识符时使用fmt.Sprintf和类似的字符串操作来构建 SQL:

col := "firstName"
sql := fmt.Sprintf("select %s from persons", col)

但这会使您面临SQL注入和引用问题,因此您需要某种白名单:

quotedColumns := map[string]string{
"firstName": "`firstName`",
"lastName": "`lastName`",
...
}
quoted, ok := quotedColumns[columnName]
if !ok {
// Do something with the error here and run away...
}
sql := fmt.Sprintf("select %s from persons", quoted)

请注意,我已经在映射的值中包含了 MySQL 反引号引用。标准接口中没有任何内容可以引用/转义标识符,因此您必须自己完成。如果您已经在手动编写白名单地图,那么您也可以包括手动引用;否则,您可以通过阅读有关引用的MySQL文档并执行几个(希望)简单的字符串操作来编写自己的标识符引用函数。

最新更新