假设我有一个结构
pub struct Student {
name: String,
age: i32,
}
我有学生类型列表,我想将其插入到 postgres 表中 在单个查询中。
我正在关注this(
UNNEST()
)它有用于基本类型列表的eg,但没有用于结构的eg。
我的代码片段
sqlx::query!(
"INSERT INTO students(name, age) SELECT * FROM UNNEST($1::text[], $2::int8[])",
&students[..]
)
.execute(&pool)
.await.unwrap();
我应该在上面的代码片段中更改什么才能一次插入多行?
就像您链接的文章中一样,您必须传递多个基元切片而不是一个复杂对象切片:
let (names, ages): (Vec<&String>, Vec<&i32>) =
students.iter().map(|Student { name, age }| (name, age));
sqlx::query!(
"INSERT INTO students(name, age) SELECT * FROM UNNEST($1::text[], $2::int8[])",
&names[..],
&ages[..]
)
.execute(&pool)
.await
.unwrap();
let (mut v_name, mut v_age) = (Vec::<String>::new(), Vec::<i32>::new());
// (vec![], vec![]) also works
students.into_iter().for_each(|s| {
v_name.push(s.name);
v_age.push(s.age);
});
sqlx::query!("
INSERT INTO students (name, age)
SELECT * FROM
UNNEST($1::text[], $2::int[])",
&v_name[..],
&v_age[..]
)
.execute(&pool)
.await?;
如果结构体
Student
有 Option
字段,如下所示,请使用 as
转换为正确的类型。
pub struct Student {
name: String,
age: i32,
note: Option<String>,
}
let (mut v_name, mut v_age, mut v_note) = (vec![], vec![], vec![]);
students.into_iter().for_each(|s| {
v_name.push(s.name);
v_age.push(s.age);
v_note.push(s.note)
});
sqlx::query!("
INSERT INTO students (name, age, note)
SELECT * FROM
UNNEST($1::text[], $2::int[], $3::text[])",
&v_name[..],
&v_age[..],
&v_note[..] as &[Option<String>] // cast is required for Option fields
)
.execute(&pool)
.await?;