mirror of
https://github.com/launchbadge/sqlx.git
synced 2025-11-04 23:42:48 +00:00
55 lines
1.6 KiB
Rust
55 lines
1.6 KiB
Rust
use super::Postgres;
|
|
use crate::{
|
|
io::BufMut,
|
|
query::QueryParameters,
|
|
encode::{IsNull, Encode},
|
|
types::HasSqlType,
|
|
};
|
|
use byteorder::{BigEndian, ByteOrder, NetworkEndian};
|
|
|
|
pub struct PostgresQueryParameters {
|
|
// OIDs of the bind parameters
|
|
pub(super) types: Vec<u32>,
|
|
// Write buffer for serializing bind values
|
|
pub(super) buf: Vec<u8>,
|
|
}
|
|
|
|
impl QueryParameters for PostgresQueryParameters {
|
|
type Backend = Postgres;
|
|
|
|
fn new() -> Self {
|
|
Self {
|
|
// Estimates for average number of bind parameters were
|
|
// chosen from sampling from internal projects
|
|
types: Vec::with_capacity(4),
|
|
buf: Vec::with_capacity(32),
|
|
}
|
|
}
|
|
|
|
fn bind<T>(&mut self, value: T)
|
|
where
|
|
Self: Sized,
|
|
Self::Backend: HasSqlType<T>,
|
|
T: Encode<Self::Backend>,
|
|
{
|
|
// TODO: When/if we receive types that do _not_ support BINARY, we need to check here
|
|
// TODO: There is no need to be explicit unless we are expecting mixed BINARY / TEXT
|
|
|
|
self.types.push(<Postgres as HasSqlType<T>>::metadata().oid);
|
|
|
|
let pos = self.buf.len();
|
|
self.buf.put_i32::<NetworkEndian>(0);
|
|
|
|
let len = if let IsNull::No = value.encode(&mut self.buf) {
|
|
(self.buf.len() - pos - 4) as i32
|
|
} else {
|
|
// Write a -1 for the len to indicate NULL
|
|
// TODO: It is illegal for [to_sql] to write any data if IsSql::No; fail a debug assertion
|
|
-1
|
|
};
|
|
|
|
// Write-back the len to the beginning of this frame (not including the len of len)
|
|
BigEndian::write_i32(&mut self.buf[pos..], len as i32);
|
|
}
|
|
}
|