如何将数组作为参数从 node.js 传递给 Vertica 查询?

How can i pass an array as a parameter to a Vertica query from node.js?

提问人:roberkules 提问时间:5/28/2023 更新时间:5/29/2023 访问量:136

问:

我正在尝试对vertica数据库执行sql查询。到目前为止,这很有效。但为了防止 sql 注入,我想使用参数化查询。看起来 Vertica 支持参数为 (与 postgres 的?$1, $2, ...)

所以参数有效,但如果参数是值数组(在条件中使用),则不行IN (...)

知道如何解决这个问题吗?


假设我有一个用户 ID 列表和一个名称:

const userIds = [1, 2, 3];
const name = 'robert'

Postgres DB(工作!

使用包:pg

const pool = new pg.Pool({ /* config */ });
const client = await pool.connect();

const { rows } = client.query(`
  SELECT * FROM users WHERE first_name = $1 AND user_id = ANY($2);
`, [name, userIds]);

用:postgres

const sql = postgres({ /* postgres db config */ });
const rows = await sql`
  SELECT * FROM users WHERE first_name = ${name} AND user_id = ANY(${userIds});
`;

vertica db(不工作)

仅当作为单个值而不是 1+ 值的数组传递时才有效userIds

用:vertica-nodejs

import Vertica from 'vertica-nodejs';
const { Pool } = Vertica;
const pool = new Pool({ /* vertica db config */ });

const res = await pool.query(`
  SELECT * FROM users WHERE first_name = ? AND user_id IN (?);
`, [name, userIds]);

// -> Invalid input syntax for integer: "{"1","2","3"}"

使用 :
似乎根本不支持参数,只是提供了一个函数 () 在字符串插值之前对其进行清理。
verticaquote

用:pg

const pool = new pg.Pool({ /* vertica db config */ });
const client = await pool.connect();

const { rows } = client.query(`
  SELECT * FROM users WHERE first_name = ? AND user_id IN (?);
`, [name, userIds]);

// -> Invalid input syntax for integer: "{"1","2","3"}"

使用 :
(似乎根本不支持连接到 Vertica 数据库)
postgres

const sql = postgres({ /* vertica db config */ });
const rows = await sql`
  SELECT * FROM users;
`;

// -> Schema "pg_catalog" does not exist

我也尝试了这些变化,而不是:user_id IN (?)

  • user_id IN (?::int[])-> 运算符不存在:int = array[int]
  • user_id = ANY (?)-> 类型“Int8Array1D”不存在
  • user_id = ANY (?::int[])-> 类型“Int8Array1D”不存在
节点.js postgresql sql注入 vertica node-postgres

评论


答:

1赞 marcothesane 5/29/2023 #1

尝试。 我不知道或SQL注入,但在bash shell中它似乎有效:ANY (ARRAY [$1])node.js

marco ~/1/Vertica/supp $ cat test.sh      
#!/usr/bin/env zsh
vsql -c "
SELECT cust_id,cust_from_dt,cust_fname,cust_lname 
FROM scd.d_customer_scd 
WHERE cust_id = ANY(ARRAY[$1]) 
ORDER BY 1,2"
marco ~/1/Vertica/supp $ ./test.sh 1,2,3
 cust_id | cust_from_dt | cust_fname | cust_lname 
---------+--------------+------------+------------
       1 | 2021-12-05   | Arthur     | Dent
       1 | 2021-12-15   | Arthur     | Dent
       1 | 2021-12-22   | Arthur     | Dent
       1 | 2021-12-29   | Arthur     | Dent
       2 | 2021-12-05   | Ford       | Prefect
       3 | 2021-11-05   | Zaphod     | Beeblebrox
       3 | 2021-12-15   | Zaphod     | Beeblebrox
       3 | 2021-12-22   | Zaphod     | Beeblebrox
       3 | 2021-12-29   | Zaphod     | Beeblebrox
(9 rows)

marco ~/1/Vertica/supp $ 

评论

0赞 roberkules 5/30/2023
我试过,传递一个整数数组。结果:WHERE user_id = ANY(ARRAY [?])Could not find array type for data type canonicalintvarchar
0赞 marcothesane 5/30/2023
请注意我如何在 shell 脚本的调用中创建整数数组:这是一个整数文字列表,逗号分隔:.没有引号,因此没有”1,2,3canonicalintvarchar"
0赞 roberkules 5/30/2023
当然,但我也将其发送为:client.query("SELECT * FROM users WHERE user_id IN (?);", [[1, 2, 3]])
0赞 marcothesane 5/31/2023
中的方括号会杀死你。你不能摆脱它们吗?[[1, 2, 3]]
0赞 marcothesane 5/31/2023
不能将任何数据作为 JSON 文本传递,需要将数据作为 SQL 文本传递。如果它们需要是字符串,则为单引号,而不是双引号。在 SQL 中,双引号(将在此处解释)包含标识符,例如列名,而不是字符串文字