簡體   English   中英

Anorm String Interpolation不替換變量

[英]Anorm String Interpolation not replacing variables

我們正在使用Scala Play,我正在嘗試確保所有SQL查詢都使用Anorm的String Interpolation。 它適用於某些查詢,但許多實際上並不在查詢執行之前替換變量。

import anorm.SQL
import anorm.SqlStringInterpolation

object SecureFile 
{
  val table = "secure_file"
  val pk = "secure_file_idx"
  ...

// This method works exactly as I would hope
def insert(secureFile: SecureFile): Option[Long] = {
  DBExec { implicit connection =>
    SQL"""
      INSERT INTO secure_file (
        subscriber_idx,
        mime_type,
        file_size_bytes,
        portal_msg_idx
      ) VALUES (
        ${secureFile.subscriberIdx},
        ${secureFile.mimeType},
        ${secureFile.fileSizeBytes},
        ${secureFile.portalMsgIdx}
        )
      """ executeInsert()
    }
  }

def delete(secureFileIdx: Long): Int = {
  DBExec { implicit connection =>
    // Prints correct values
    println(s"table: ${table} pk: ${pk} secureFileIdx: ${secureFileIdx} ")

    // Does not work
    SQL""" 
      DELETE FROM $table WHERE ${pk} = ${secureFileIdx} 
    """.executeUpdate()

    // Works, but unsafe
    val query = s"DELETE FROM ${table} WHERE ${pk} = ${secureFileIdx}" 
    SQL(query).executeUpdate() 
  }
}
....
}

在PostgreSQL日志中,很明顯delete語句沒有獲取正確的值:

2015-01-09 17:23:03 MST ERROR:  syntax error at or near "$1" at character 23
2015-01-09 17:23:03 MST STATEMENT: DELETE FROM $1 WHERE $2 = $3
2015-01-09 17:23:03 MST LOG:  execute S_1: ROLLBACK

我已經嘗試了許多execute,executeUpdate和executeQuery的變種,但結果相似。 目前,我們正在使用基本的字符串替換,但當然這很糟糕,因為它沒有使用PreparedStatements。

引入Anorm字符串插值來傳遞參數(例如SQL"Select * From Test Where id = $x )”,根據正確的類型轉換,在底層PreparedStament上設置插值參數(例如$x )(請參閱https:// www。 playframework.com/documentation/2.3.x/ScalaAnorm )。

下一個Anorm版本還將使用#$foo語法將參數插值與標准字符串插值混合。 這將允許寫入DELETE FROM #$table WHERE #${pk} = ${secureFileIdx}並將其作為DELETE FROM foo WHERE bar = ?執行DELETE FROM foo WHERE bar = ? (如果文字table"foo"pk"bar" ), secureFileIdx文字secureFileIdx作為參數傳遞。 查看相關的拉取請求

在下一版本發布之前,您可以從其主要來源構建Anorm,並從此更改中受益。

對於坐在這個頁面上的任何人都撓頭,想知道他們可能會遺漏什么......

SQL("select * from mytable where id = $id") 

是不一樣的

SQL"select * from mytable where id = $id" 

前者不進行字符串插值,而后者則進行字符串插值。

在上述文檔中很容易忽略這一點,因為所提供的所有樣本恰好都有一個(非相關的)右括號(就像這句話一樣)

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM