diff options
Diffstat (limited to '')
| -rw-r--r-- | wyrd_sqlite/src/params.rs | 92 |
1 files changed, 92 insertions, 0 deletions
diff --git a/wyrd_sqlite/src/params.rs b/wyrd_sqlite/src/params.rs new file mode 100644 index 0000000..4561c40 --- /dev/null +++ b/wyrd_sqlite/src/params.rs @@ -0,0 +1,92 @@ +use std::ffi::{c_double, c_int}; + +use variadics_please::all_tuples_enumerated; + +use crate::{Result, Statement, ffi}; + +mod sealed { + pub trait Sealed {} +} + +use sealed::Sealed; + +pub trait Param: Sealed { + #[doc(hidden)] + fn __bind_in(&self, stmt: &mut Statement<'_>, i: c_int) -> Result<()>; +} + +pub trait Params: Sealed { + #[doc(hidden)] + fn __bind_in(&self, stmt: &mut Statement<'_>) -> Result<()>; +} + +impl Sealed for c_int {} +impl Param for c_int { + #[inline] + fn __bind_in(&self, stmt: &mut Statement<'_>, i: c_int) -> Result<()> { + stmt.bind_i32(i, *self) + } +} + +impl Sealed for ffi::sqlite3_int64 {} +impl Param for ffi::sqlite3_int64 { + #[inline] + fn __bind_in(&self, stmt: &mut Statement<'_>, i: c_int) -> Result<()> { + stmt.bind_i64(i, *self) + } +} + +impl Sealed for c_double {} +impl Param for c_double { + #[inline] + fn __bind_in(&self, stmt: &mut Statement<'_>, i: c_int) -> Result<()> { + stmt.bind_double(i, *self) + } +} + +impl<T: Param> Sealed for Option<T> {} +impl<T: Param> Param for Option<T> { + fn __bind_in(&self, stmt: &mut Statement<'_>, i: c_int) -> Result<()> { + match self.as_ref() { + Some(v) => v.__bind_in(stmt, i), + // explicitly binding NULL is required in case a previous call bound a value here + None => stmt.bind_null(i), + } + } +} + +impl Sealed for () {} +impl Param for () { + #[inline] + fn __bind_in(&self, stmt: &mut Statement<'_>, i: c_int) -> Result<()> { + stmt.bind_null(i) + } +} + +impl Params for () { + fn __bind_in(&self, _stmt: &mut Statement<'_>) -> Result<()> { + Ok(()) + } +} + +macro_rules! impl_params { + ($(($i:tt, $T:ident)),*) => { + impl<$($T:Param),*> Sealed for ($($T,)*) {} + impl<$($T:Param),*> Params for ($($T,)*) { + fn __bind_in(&self, stmt: &mut Statement<'_>) -> Result<()> { + $(self.$i.__bind_in(stmt, $i + 1)?;)* + Ok(()) + } + } + + impl<$($T:Param),*> Sealed for ($(($T, c_int),)*) {} + impl<$($T:Param),*> Params for ($(($T, c_int),)*) { + fn __bind_in(&self, stmt: &mut Statement<'_>) -> Result<()> { + $(self.$i.0.__bind_in(stmt, self.$i.1)?;)* + Ok(()) + } + } + } +} + +all_tuples_enumerated!(impl_params, 1, 12, T); |