在 WHERE 子句中使用自定义 SQL 函数很热门

Hot to use custom SQL functions in the WHERE clause

我正在尝试使用 Knex.js.

创建一个将自定义函数应用于列的 where 子句

假设我有一个名为 tableName 的 table,其列名为 col1, col2, col3,还有一个函数 f 作为参数接收与在 col1col2.

我还有两个名为 var1var2 的变量(预先定义),它们与 f 返回的对象类型相同。我尝试了一些方法。

示例 1:

let rows = knexClient("tableName").whereRaw('f(?) <= ${var1} AND f(?) >= ${var2}', [col1, col2]).then((rows) => {
  for (row of rows) {
    console.log('${row["col1"]} ${row["col2"]} ${row["col3"]}');
  }
}).catch((err) => {
  console.log(err);
  throw err;
});

这会产生以下错误:

ReferenceError: col1 is not defined.

示例 2:

let rows = knexClient("tableName").whereRaw("f(col1) <= ? AND f(col2) >= ?", [var1, var2]).then((rows) => {
  for (row of rows) {
    console.log('${row["col1"]} ${row["col2"]} ${row["col3"]}');
  }
}).catch((err) => {
  console.log(err);
  throw err;
});

这会产生以下错误:

SQLITE_ERROR: no such column: col1] {
  errno: 1,
  code: 'SQLITE_ERROR'
}

正确的做法是什么?我四处搜索,看到有人在做与我第一次尝试类似的事情 。但它对我不起作用。

您不能动态绑定列名称(即使用 ? 占位符),这仅适用于值。

以下:

var var1 = 10, var2 = 20;

knex("tableName")
    .whereRaw("f(col1) <= ?", var1)
    .whereRaw("f(col2) => ?", var2)
    .select();

生成的 SQL 结果如下:

select
  *
from
  tableName
where
  f(col1) <= 10
  and f(col2) => 20

如果您有包含目标列名的变量,您需要自己格式化它们:

var col1 = "some_col", col2 = "other_col";
var var1 = 10, var2 = 20;

knex("tableName")
    .whereRaw(`f(${col1}) <= ?`, var1)
    .whereRaw(`f(${col2}) => ?`, var2)
    .select();

产生

select
  *
from
  tableName
where
  f(some_col) <= 10
  and f(other_col) => 20