1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134
use crate::types::Primative; use crate::types::{Bind, Field}; use crate::Table; use std::{fmt::Write, marker::PhantomData}; pub trait Predicate { fn write_predicate(&self, sql: &mut String); } pub struct And<H, T> { pub(crate) head: H, pub(crate) tail: T, } impl<H, T> Predicate for And<H, T> where H: Predicate, T: Predicate, { fn write_predicate(&self, sql: &mut String) { self.head.write_predicate(sql); sql.push_str(" AND "); self.tail.write_predicate(sql); } } pub struct Or<H, T> { pub(crate) head: H, pub(crate) tail: T, } impl<H, T> Predicate for Or<H, T> where H: Predicate, T: Predicate, { fn write_predicate(&self, sql: &mut String) { self.head.write_predicate(sql); sql.push_str(" OR "); self.tail.write_predicate(sql); } } pub trait Operator { fn write_operator(sql: &mut String); } pub struct Eq; impl Operator for Eq { fn write_operator(sql: &mut String) { sql.push('='); } } pub struct Neq; impl Operator for Neq { fn write_operator(sql: &mut String) { sql.push_str("!="); } } pub struct Gt; impl Operator for Gt { fn write_operator(sql: &mut String) { sql.push('>'); } } pub struct Lt; impl Operator for Lt { fn write_operator(sql: &mut String) { sql.push('<'); } } pub struct Op<T, A, U, O> { lhs: Field<T, A>, rhs: U, _operator: PhantomData<O>, } impl<T, A, U, O> Op<T, A, U, O> { pub(crate) fn new(lhs: Field<T, A>, rhs: U) -> Self { Self { lhs, rhs, _operator: PhantomData, } } } impl<T, A, U, O> Predicate for Op<T, A, U, O> where T: Table, U: Primative, O: Operator, { fn write_predicate(&self, sql: &mut String) { self.lhs.write_field(sql); sql.push(' '); O::write_operator(sql); sql.push(' '); self.rhs.write_primative(sql); } } impl<T, T2, A, O> Predicate for Op<T, A, Field<T2, A>, O> where T: Table, T2: Table, O: Operator, { fn write_predicate(&self, sql: &mut String) { self.lhs.write_field(sql); O::write_operator(sql); self.rhs.write_field(sql); } } impl<T, A, O> Predicate for Op<T, A, Bind, O> where T: Table, O: Operator, { fn write_predicate(&self, sql: &mut String) { self.lhs.write_field(sql); O::write_operator(sql); sql.write_fmt(format_args!("${}", self.rhs.n)).unwrap(); } }