drizzle_sqlite/values/
insert.rs1use core::marker::PhantomData;
6
7use crate::prelude::*;
8use drizzle_core::{Placeholder, SQL, SQLParam, TypedPlaceholder};
9
10use super::{OwnedSQLiteValue, SQLiteValue};
11
12#[doc(hidden)]
13#[derive(Debug, Clone)]
14pub struct ValueWrapper<'a, V: SQLParam, T> {
15 pub value: SQL<'a, V>,
16 pub _phantom: PhantomData<T>,
17}
18
19impl<'a, V: SQLParam, T> ValueWrapper<'a, V, T> {
20 pub const fn new<U>(value: SQL<'a, V>) -> ValueWrapper<'a, V, U> {
21 ValueWrapper {
22 value,
23 _phantom: PhantomData,
24 }
25 }
26}
27
28#[derive(Debug, Clone, Default)]
30#[allow(clippy::large_enum_variant)]
31pub enum SQLiteInsertValue<'a, V: SQLParam, T> {
32 #[default]
34 Omit,
35 Null,
37 Value(ValueWrapper<'a, V, T>),
39}
40
41impl<'a, T> SQLiteInsertValue<'a, SQLiteValue<'a>, T> {
42 #[must_use]
44 pub fn into_owned(self) -> SQLiteInsertValue<'static, SQLiteValue<'static>, T> {
45 match self {
46 SQLiteInsertValue::Omit => SQLiteInsertValue::Omit,
47 SQLiteInsertValue::Null => SQLiteInsertValue::Null,
48 SQLiteInsertValue::Value(wrapper) => {
49 let static_sql = match wrapper.value.chunks.first() {
51 Some(drizzle_core::SQLChunk::Param(param)) => param.value.as_ref().map_or_else(
52 || drizzle_core::SQL::param(SQLiteValue::Null),
53 |val| {
54 let owned_val = OwnedSQLiteValue::from(val.as_ref().clone());
55 let static_val: SQLiteValue<'static> = owned_val.into();
56 drizzle_core::SQL::param(static_val)
57 },
58 ),
59 _ => drizzle_core::SQL::param(SQLiteValue::Null),
60 };
61 SQLiteInsertValue::Value(ValueWrapper::<SQLiteValue<'static>, T>::new(static_sql))
62 }
63 }
64 }
65}
66
67impl<'a, T, U> From<T> for SQLiteInsertValue<'a, SQLiteValue<'a>, U>
68where
69 T: TryInto<SQLiteValue<'a>> + TryInto<U>,
70 U: TryInto<SQLiteValue<'a>>,
71{
72 fn from(value: T) -> Self {
73 let sql = TryInto::<U>::try_into(value)
74 .map(|v| v.try_into().unwrap_or_default())
75 .map_or_else(
76 |_| SQL::from(SQLiteValue::Null),
77 |v: SQLiteValue<'a>| SQL::from(v),
78 );
79 SQLiteInsertValue::Value(ValueWrapper::<SQLiteValue<'a>, T>::new(sql))
80 }
81}
82
83impl<'a, T> From<Placeholder> for SQLiteInsertValue<'a, SQLiteValue<'a>, T> {
84 fn from(placeholder: Placeholder) -> Self {
85 use drizzle_core::{Param, SQLChunk};
86 let chunk = SQLChunk::Param(Param {
87 placeholder,
88 value: None,
89 });
90 SQLiteInsertValue::Value(ValueWrapper::<SQLiteValue<'a>, T>::new(
91 core::iter::once(chunk).collect(),
92 ))
93 }
94}
95
96impl<'a, M: drizzle_core::types::DataType, N: drizzle_core::expr::Nullability, T>
97 From<TypedPlaceholder<M, N>> for SQLiteInsertValue<'a, SQLiteValue<'a>, T>
98{
99 fn from(typed: TypedPlaceholder<M, N>) -> Self {
100 Placeholder::from(typed).into()
101 }
102}
103
104impl<'a, const N: usize> From<[u8; N]> for SQLiteInsertValue<'a, SQLiteValue<'a>, Vec<u8>> {
106 fn from(value: [u8; N]) -> Self {
107 let sqlite_value = SQLiteValue::Blob(Cow::Owned(value.to_vec()));
108 let sql = SQL::param(sqlite_value);
109 SQLiteInsertValue::Value(ValueWrapper::<SQLiteValue<'a>, Vec<u8>>::new(sql))
110 }
111}