diff --git a/src/query/helper.rs b/src/query/helper.rs index 6ab31d53b..56b880e2b 100644 --- a/src/query/helper.rs +++ b/src/query/helper.rs @@ -8,6 +8,8 @@ use sea_query::{ }; pub use sea_query::{Condition, ConditionalStatement, DynIden, JoinType, Order, OrderedStatement}; +use sea_query::IntoColumnRef; + // LINT: when the column does not appear in tables selected from // LINT: when there is a group by clause, but some columns don't have aggregate functions // LINT: when the join table or column does not exists @@ -149,6 +151,61 @@ pub trait QuerySelect: Sized { self } + /// Add a DISTINCT expression + /// ``` + /// use sea_orm::{entity::*, query::*, tests_cfg::cake, DbBackend}; + /// struct Input { + /// name: Option, + /// } + /// let input = Input { + /// name: Some("cheese".to_owned()), + /// }; + /// assert_eq!( + /// cake::Entity::find() + /// .filter( + /// Condition::all().add_option(input.name.map(|n| cake::Column::Name.contains(&n))) + /// ) + /// .distinct() + /// .build(DbBackend::MySql) + /// .to_string(), + /// "SELECT DISTINCT `cake`.`id`, `cake`.`name` FROM `cake` WHERE `cake`.`name` LIKE '%cheese%'" + /// ); + /// ``` + fn distinct(mut self) -> Self { + self.query().distinct(); + self + } + + /// Add a DISTINCT ON expression + /// NOTE: this function is only supported by `sqlx-postgres` + /// ``` + /// use sea_orm::{entity::*, query::*, tests_cfg::cake, DbBackend}; + /// struct Input { + /// name: Option, + /// } + /// let input = Input { + /// name: Some("cheese".to_owned()), + /// }; + /// assert_eq!( + /// cake::Entity::find() + /// .filter( + /// Condition::all().add_option(input.name.map(|n| cake::Column::Name.contains(&n))) + /// ) + /// .distinct_on([cake::Column::Name]) + /// .build(DbBackend::Postgres) + /// .to_string(), + /// "SELECT DISTINCT ON (\"name\") \"cake\".\"id\", \"cake\".\"name\" FROM \"cake\" WHERE \"cake\".\"name\" LIKE '%cheese%'" + /// ); + /// ``` + fn distinct_on(mut self, cols: I) -> Self + where + T: IntoColumnRef, + I: IntoIterator, + { + self.query().distinct_on(cols); + self + } + #[doc(hidden)] fn join_join(mut self, join: JoinType, rel: RelationDef, via: Option) -> Self { if let Some(via) = via {