209 lines
4.8 KiB
Rust
209 lines
4.8 KiB
Rust
use sqlx::MySql;
|
|
use sqlx::mysql::MySqlArguments;
|
|
use sqlx::query::{Query, QueryAs, QueryScalar};
|
|
use sqlx::types::chrono::{NaiveDate, NaiveDateTime};
|
|
|
|
pub type DB = MySql;
|
|
#[derive(Clone, Debug)]
|
|
pub enum Value {
|
|
Int8(i8),
|
|
Uint8(u8),
|
|
Int16(i16),
|
|
Uint16(u16),
|
|
Int32(i32),
|
|
Uint32(u32),
|
|
Int64(i64),
|
|
Uint64(u64),
|
|
VecU8(Vec<u8>),
|
|
String(String),
|
|
Bool(bool),
|
|
Uuid(uuid::Uuid),
|
|
NaiveDate(NaiveDate),
|
|
NaiveDateTime(NaiveDateTime),
|
|
}
|
|
|
|
pub enum Updater<'a> {
|
|
Set(&'a str, Value),
|
|
Increment(&'a str, Value),
|
|
Decrement(&'a str, Value),
|
|
}
|
|
#[deprecated(since = "0.1.0", note = "Please use Value instead")]
|
|
pub type SqlValue = Value;
|
|
|
|
macro_rules! bind_value {
|
|
($query:expr, $value: expr) => {{
|
|
let query = match $value {
|
|
Value::Int8(v) => $query.bind(v),
|
|
Value::Uint8(v) => $query.bind(v),
|
|
Value::Int16(v) => $query.bind(v),
|
|
Value::Uint16(v) => $query.bind(v),
|
|
Value::Int32(v) => $query.bind(v),
|
|
Value::Uint32(v) => $query.bind(v),
|
|
Value::Int64(v) => $query.bind(v),
|
|
Value::Uint64(v) => $query.bind(v),
|
|
Value::VecU8(v) => $query.bind(v),
|
|
Value::String(v) => $query.bind(v),
|
|
Value::Bool(v) => $query.bind(v),
|
|
Value::Uuid(v) => $query.bind(v),
|
|
Value::NaiveDate(v) => $query.bind(v),
|
|
Value::NaiveDateTime(v) => $query.bind(v),
|
|
};
|
|
query
|
|
}};
|
|
}
|
|
|
|
pub fn bind_values<'q>(query: Query<'q, DB, MySqlArguments>, values: &'q [Value]) -> Query<'q, DB, MySqlArguments> {
|
|
let mut query = query;
|
|
for value in values {
|
|
query = bind_value!(query, value);
|
|
}
|
|
query
|
|
}
|
|
|
|
|
|
pub fn bind_as_values<'q, O>(query: QueryAs<'q, DB, O, MySqlArguments>, values: &'q [Value]) -> QueryAs<'q, DB, O, MySqlArguments> {
|
|
values.into_iter().fold(query, |query, value| {
|
|
bind_value!(query, value)
|
|
})
|
|
}
|
|
|
|
pub fn bind_scalar_values<'q, O>(query: QueryScalar<'q, DB, O, MySqlArguments>, values: &'q [Value]) -> QueryScalar<'q, DB, O, MySqlArguments> {
|
|
let mut query = query;
|
|
for value in values {
|
|
query = bind_value!(query, value);
|
|
}
|
|
query
|
|
}
|
|
|
|
#[inline]
|
|
pub fn query_fields(fields: Vec<&str>) -> String {
|
|
fields.iter().filter_map(|e| e.split(" ").next())
|
|
.collect::<Vec<_>>().join(", ")
|
|
}
|
|
|
|
impl From<String> for Value {
|
|
fn from(value: String) -> Self {
|
|
Value::String(value)
|
|
}
|
|
}
|
|
|
|
impl From<i32> for Value {
|
|
fn from(value: i32) -> Self {
|
|
Value::Int32(value)
|
|
}
|
|
}
|
|
|
|
impl From<i64> for Value {
|
|
fn from(value: i64) -> Self {
|
|
Value::Int64(value)
|
|
}
|
|
}
|
|
|
|
impl From<bool> for Value {
|
|
fn from(value: bool) -> Self {
|
|
Value::Bool(value)
|
|
}
|
|
}
|
|
|
|
impl From<uuid::Uuid> for Value {
|
|
fn from(value: uuid::Uuid) -> Self {
|
|
Value::Uuid(value)
|
|
}
|
|
}
|
|
|
|
impl From<&str> for Value {
|
|
fn from(value: &str) -> Self {
|
|
Value::String(value.to_string())
|
|
}
|
|
}
|
|
|
|
impl From<&i32> for Value {
|
|
fn from(value: &i32) -> Self {
|
|
Value::Int32(*value)
|
|
}
|
|
}
|
|
|
|
impl From<&i64> for Value {
|
|
fn from(value: &i64) -> Self {
|
|
Value::Int64(*value)
|
|
}
|
|
}
|
|
|
|
impl From<&bool> for Value {
|
|
fn from(value: &bool) -> Self {
|
|
Value::Bool(*value)
|
|
}
|
|
}
|
|
|
|
impl From<&uuid::Uuid> for Value {
|
|
fn from(value: &uuid::Uuid) -> Self {
|
|
Value::Uuid(*value)
|
|
}
|
|
}
|
|
|
|
impl From<NaiveDate> for Value {
|
|
fn from(value: NaiveDate) -> Self {
|
|
Value::NaiveDate(value)
|
|
}
|
|
}
|
|
|
|
impl From<NaiveDateTime> for Value {
|
|
fn from(value: NaiveDateTime) -> Self {
|
|
Value::NaiveDateTime(value)
|
|
}
|
|
}
|
|
|
|
pub trait BindValues<'q> {
|
|
type Output;
|
|
|
|
fn bind_values(self, values: &'q [Value]) -> Self::Output;
|
|
}
|
|
|
|
impl<'q> BindValues<'q> for Query<'q, DB, MySqlArguments> {
|
|
type Output = Query<'q, DB, MySqlArguments>;
|
|
|
|
fn bind_values(self, values: &'q [Value]) -> Self::Output {
|
|
let mut query = self;
|
|
for value in values {
|
|
query = bind_value!(query, value);
|
|
}
|
|
query
|
|
}
|
|
}
|
|
|
|
impl<'q, O> BindValues<'q> for QueryAs<'q, DB, O, MySqlArguments> {
|
|
type Output = QueryAs<'q, DB, O, MySqlArguments>;
|
|
|
|
fn bind_values(self, values: &'q [Value]) -> Self::Output {
|
|
values.into_iter().fold(self, |query, value| {
|
|
bind_value!(query, value)
|
|
})
|
|
}
|
|
}
|
|
|
|
impl<'q, O> BindValues<'q> for QueryScalar<'q, DB, O, MySqlArguments> {
|
|
type Output = QueryScalar<'q, DB, O, MySqlArguments>;
|
|
|
|
fn bind_values(self, values: &'q [Value]) -> Self::Output {
|
|
let mut query = self;
|
|
for value in values {
|
|
query = bind_value!(query, value);
|
|
}
|
|
query
|
|
}
|
|
}
|
|
|
|
|
|
#[macro_export]
|
|
macro_rules! values {
|
|
() => {
|
|
vec![]
|
|
};
|
|
($x:expr) => {
|
|
vec![<$crate::prelude::Value>::from($x)]
|
|
};
|
|
($($x:expr),+ $(,)?) => {
|
|
vec![$(<$crate::prelude::Value>::from($x)),+]
|
|
};
|
|
}
|