use crate::orm::model_query::ModelQuery;
use crate::orm::postgres::model::PgModel;
#[derive(Debug, Clone)]
pub struct SortBuilder<M> {
allowed: Vec<String>,
sorts: Vec<(String, bool)>,
_marker: std::marker::PhantomData<M>,
}
impl<M: PgModel + Sync> SortBuilder<M> {
pub fn new() -> Self {
Self {
allowed: Vec::new(),
sorts: Vec::new(),
_marker: std::marker::PhantomData,
}
}
pub fn allow(mut self, col: impl Into<String>) -> Self {
self.allowed.push(col.into());
self
}
pub fn apply_user_input(mut self, col: &str, asc: bool) -> Self {
if self.allowed.iter().any(|a| a == col) {
self.sorts.push((col.to_owned(), asc));
}
self
}
pub fn then_by(mut self, col: impl Into<String>, asc: bool) -> Self {
self.sorts.push((col.into(), asc));
self
}
pub fn apply(&self, mut query: ModelQuery<M>) -> ModelQuery<M> {
for (col, asc) in &self.sorts {
query = if *asc {
query.order_by(col)
} else {
query.order_by_desc(col)
};
}
query
}
}
impl<M: PgModel + Sync> Default for SortBuilder<M> {
fn default() -> Self {
Self::new()
}
}