sea_query/expr.rs
1//! Building blocks of SQL statements.
2//!
3//! [`Expr`] is an arbitrary, dynamically-typed SQL expression.
4//! It can be used in select fields, where clauses and many other places.
5//!
6//! [`ExprTrait`] provides "operator" methods for building expressions.
7
8use crate::{func::*, query::*, types::*, value::*};
9
10/// A legacy compatibility alias for [`Expr`].
11///
12/// These used to be two separate (but very similar) types.
13pub type SimpleExpr = Expr;
14
15/// An arbitrary, dynamically-typed SQL expression.
16///
17/// It can be used in select fields, where clauses and many other places.
18///
19/// More concreterly, under the hood [`Expr`]s can be:
20///
21/// - Rust values
22/// - SQL identifiers
23/// - SQL function calls
24/// - various operators and sub-queries
25///
26/// If something is not supported here, look into [`BinOper::Custom`],
27/// [`Func::cust`], or [`Expr::cust*`][`Expr::cust_with_values`] as a
28/// workaround, and consider reporting your issue.
29#[derive(Debug, Clone, PartialEq)]
30#[non_exhaustive]
31pub enum Expr {
32 Column(ColumnRef),
33 Tuple(Vec<Expr>),
34 Unary(UnOper, Box<Expr>),
35 FunctionCall(FunctionCall),
36 Binary(Box<Expr>, BinOper, Box<Expr>),
37 SubQuery(Option<SubQueryOper>, Box<SubQueryStatement>),
38 Value(Value),
39 Values(Vec<Value>),
40 Custom(String),
41 CustomWithExpr(String, Vec<Expr>),
42 Keyword(Keyword),
43 AsEnum(DynIden, Box<Expr>),
44 Case(Box<CaseStatement>),
45 Constant(Value),
46 TypeName(TypeRef),
47}
48
49/// "Operator" methods for building expressions.
50///
51/// Before `sea_query` 0.32.0 (`sea_orm` 1.1.1),
52/// these methods were awailable only on [`Expr`]/[`SimpleExpr`]
53/// and you needed to manually construct these types first.
54///
55/// Now, you can call them directly on any expression type:
56///
57/// ```no_run
58/// # use sea_query::*;
59/// #
60/// let expr = 1_i32.cast_as("REAL");
61/// let expr = Func::char_length("abc").eq(3_i32);
62/// let expr = Expr::current_date().cast_as("TEXT").like("2024%");
63/// ```
64///
65/// If some methods are missing, look into [`BinOper::Custom`], [`Func::cust`],
66/// or [`Expr::cust*`][`Expr::cust_with_values`] as a workaround, and consider
67/// reporting your issue.
68pub trait ExprTrait: Sized {
69 /// Express an arithmetic addition operation.
70 ///
71 /// # Examples
72 ///
73 /// Adding literal values
74 ///
75 /// ```
76 /// use sea_query::{tests_cfg::*, *};
77 ///
78 /// let query = Query::select()
79 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
80 /// .from(Char::Table)
81 /// .and_where(1.add(1).eq(2))
82 /// .to_owned();
83 ///
84 /// assert_eq!(
85 /// query.to_string(MysqlQueryBuilder),
86 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE 1 + 1 = 2"#
87 /// );
88 /// assert_eq!(
89 /// query.to_string(PostgresQueryBuilder),
90 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE 1 + 1 = 2"#
91 /// );
92 /// assert_eq!(
93 /// query.to_string(SqliteQueryBuilder),
94 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE 1 + 1 = 2"#
95 /// );
96 /// ```
97 ///
98 /// Adding columns and values
99 ///
100 /// ```
101 /// use sea_query::{tests_cfg::*, *};
102 ///
103 /// let query = Query::select()
104 /// .expr(Expr::col(Char::SizeW).add(1))
105 /// .from(Char::Table)
106 /// .to_owned();
107 ///
108 /// assert_eq!(
109 /// query.to_string(MysqlQueryBuilder),
110 /// r#"SELECT `size_w` + 1 FROM `character`"#
111 /// );
112 /// assert_eq!(
113 /// query.to_string(PostgresQueryBuilder),
114 /// r#"SELECT "size_w" + 1 FROM "character""#
115 /// );
116 /// assert_eq!(
117 /// query.to_string(SqliteQueryBuilder),
118 /// r#"SELECT "size_w" + 1 FROM "character""#
119 /// );
120 /// ```
121 ///
122 /// Adding columns
123 ///
124 /// ```
125 /// use sea_query::{tests_cfg::*, *};
126 ///
127 /// let query = Query::select()
128 /// .expr(Expr::col(Char::SizeW).add(Expr::col(Char::SizeH)))
129 /// .from(Char::Table)
130 /// .to_owned();
131 ///
132 /// assert_eq!(
133 /// query.to_string(MysqlQueryBuilder),
134 /// r#"SELECT `size_w` + `size_h` FROM `character`"#
135 /// );
136 /// assert_eq!(
137 /// query.to_string(PostgresQueryBuilder),
138 /// r#"SELECT "size_w" + "size_h" FROM "character""#
139 /// );
140 /// assert_eq!(
141 /// query.to_string(SqliteQueryBuilder),
142 /// r#"SELECT "size_w" + "size_h" FROM "character""#
143 /// );
144 /// ```
145 fn add<R>(self, right: R) -> Expr
146 where
147 R: Into<Expr>,
148 {
149 self.binary(BinOper::Add, right)
150 }
151
152 /// Express a `AS enum` expression.
153 ///
154 /// # Examples
155 ///
156 /// ```
157 /// use sea_query::{tests_cfg::*, *};
158 ///
159 /// let query = Query::insert()
160 /// .into_table(Char::Table)
161 /// .columns([Char::FontSize])
162 /// .values_panic(["large".as_enum("FontSizeEnum")])
163 /// .to_owned();
164 ///
165 /// assert_eq!(
166 /// query.to_string(MysqlQueryBuilder),
167 /// r#"INSERT INTO `character` (`font_size`) VALUES ('large')"#
168 /// );
169 /// assert_eq!(
170 /// query.to_string(PostgresQueryBuilder),
171 /// r#"INSERT INTO "character" ("font_size") VALUES (CAST('large' AS "FontSizeEnum"))"#
172 /// );
173 /// assert_eq!(
174 /// query.to_string(SqliteQueryBuilder),
175 /// r#"INSERT INTO "character" ("font_size") VALUES ('large')"#
176 /// );
177 ///
178 /// let query = Query::select()
179 /// .expr(Expr::col(Char::FontSize).as_enum("FontSizeEnum[]"))
180 /// .from(Char::Table)
181 /// .to_owned();
182 ///
183 /// assert_eq!(
184 /// query.to_string(PostgresQueryBuilder),
185 /// r#"SELECT CAST("font_size" AS "FontSizeEnum"[]) FROM "character""#
186 /// );
187 /// ```
188 #[allow(clippy::wrong_self_convention)]
189 fn as_enum<N>(self, type_name: N) -> Expr
190 where
191 N: IntoIden;
192
193 /// Express a logical `AND` operation.
194 ///
195 /// # Examples
196 ///
197 /// ```
198 /// use sea_query::{*, tests_cfg::*};
199 ///
200 /// let query = Query::select()
201 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
202 /// .from(Char::Table)
203 /// .cond_where(any![
204 /// Expr::col(Char::SizeW).eq(1).and(Expr::col(Char::SizeH).eq(2)),
205 /// Expr::col(Char::SizeW).eq(3).and(Expr::col(Char::SizeH).eq(4)),
206 /// ])
207 /// .to_owned();
208 ///
209 /// assert_eq!(
210 /// query.to_string(MysqlQueryBuilder),
211 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE (`size_w` = 1 AND `size_h` = 2) OR (`size_w` = 3 AND `size_h` = 4)"#
212 /// );
213 /// assert_eq!(
214 /// query.to_string(PostgresQueryBuilder),
215 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE ("size_w" = 1 AND "size_h" = 2) OR ("size_w" = 3 AND "size_h" = 4)"#
216 /// );
217 /// assert_eq!(
218 /// query.to_string(SqliteQueryBuilder),
219 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE ("size_w" = 1 AND "size_h" = 2) OR ("size_w" = 3 AND "size_h" = 4)"#
220 /// );
221 /// ```
222 fn and<R>(self, right: R) -> Expr
223 where
224 R: Into<Expr>,
225 {
226 self.binary(BinOper::And, right)
227 }
228
229 /// Express a `BETWEEN` expression.
230 ///
231 /// # Examples
232 ///
233 /// ```
234 /// use sea_query::{*, tests_cfg::*};
235 ///
236 /// let query = Query::select()
237 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
238 /// .from(Char::Table)
239 /// .and_where((Char::Table, Char::SizeW).into_column_ref().between(1, 10))
240 /// .to_owned();
241 ///
242 /// assert_eq!(
243 /// query.to_string(MysqlQueryBuilder),
244 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE `character`.`size_w` BETWEEN 1 AND 10"#
245 /// );
246 /// assert_eq!(
247 /// query.to_string(PostgresQueryBuilder),
248 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "character"."size_w" BETWEEN 1 AND 10"#
249 /// );
250 /// assert_eq!(
251 /// query.to_string(SqliteQueryBuilder),
252 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "character"."size_w" BETWEEN 1 AND 10"#
253 /// );
254 /// ```
255 fn between<A, B>(self, a: A, b: B) -> Expr
256 where
257 A: Into<Expr>,
258 B: Into<Expr>,
259 {
260 self.binary(
261 BinOper::Between,
262 Expr::Binary(Box::new(a.into()), BinOper::And, Box::new(b.into())),
263 )
264 }
265
266 /// Create any binary operation
267 ///
268 /// # Examples
269 /// ```
270 /// use sea_query::{*, tests_cfg::*};
271 ///
272 /// let query = Query::select()
273 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
274 /// .from(Char::Table)
275 /// .cond_where(all![
276 /// Char::SizeW.into_column_ref().binary(BinOper::SmallerThan, 10),
277 /// Char::SizeW.into_column_ref().binary(BinOper::GreaterThan, Char::SizeH.into_column_ref())
278 /// ])
279 /// .to_owned();
280 /// assert_eq!(
281 /// query.to_string(MysqlQueryBuilder),
282 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE `size_w` < 10 AND `size_w` > `size_h`"#
283 /// );
284 /// assert_eq!(
285 /// query.to_string(PostgresQueryBuilder),
286 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "size_w" < 10 AND "size_w" > "size_h""#
287 /// );
288 /// assert_eq!(
289 /// query.to_string(SqliteQueryBuilder),
290 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "size_w" < 10 AND "size_w" > "size_h""#
291 /// );
292 /// ```
293 fn binary<O, R>(self, op: O, right: R) -> Expr
294 where
295 O: Into<BinOper>,
296 R: Into<Expr>;
297
298 /// Express a `CAST AS` expression.
299 ///
300 /// # Examples
301 ///
302 /// ```
303 /// use sea_query::{tests_cfg::*, *};
304 ///
305 /// let query = Query::select().expr("1".cast_as("integer")).to_owned();
306 ///
307 /// assert_eq!(
308 /// query.to_string(MysqlQueryBuilder),
309 /// r#"SELECT CAST('1' AS integer)"#
310 /// );
311 /// assert_eq!(
312 /// query.to_string(PostgresQueryBuilder),
313 /// r#"SELECT CAST('1' AS integer)"#
314 /// );
315 /// assert_eq!(
316 /// query.to_string(SqliteQueryBuilder),
317 /// r#"SELECT CAST('1' AS integer)"#
318 /// );
319 /// ```
320 fn cast_as<N>(self, type_name: N) -> Expr
321 where
322 N: IntoIden;
323
324 /// Express an arithmetic division operation.
325 ///
326 /// # Examples
327 ///
328 /// ```
329 /// use sea_query::{tests_cfg::*, *};
330 ///
331 /// let query = Query::select()
332 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
333 /// .from(Char::Table)
334 /// .and_where(1.div(1).eq(2))
335 /// .to_owned();
336 ///
337 /// assert_eq!(
338 /// query.to_string(MysqlQueryBuilder),
339 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE 1 / 1 = 2"#
340 /// );
341 /// assert_eq!(
342 /// query.to_string(PostgresQueryBuilder),
343 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE 1 / 1 = 2"#
344 /// );
345 /// assert_eq!(
346 /// query.to_string(SqliteQueryBuilder),
347 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE 1 / 1 = 2"#
348 /// );
349 /// ```
350 fn div<R>(self, right: R) -> Expr
351 where
352 R: Into<Expr>,
353 {
354 self.binary(BinOper::Div, right)
355 }
356
357 /// Express an equal (`=`) expression.
358 ///
359 /// # Examples
360 ///
361 /// ```
362 /// use sea_query::{tests_cfg::*, *};
363 ///
364 /// let query = Query::select()
365 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
366 /// .from(Char::Table)
367 /// .and_where(Expr::val("What!").eq("Nothing"))
368 /// .and_where(Char::Id.into_column_ref().eq(1))
369 /// .to_owned();
370 ///
371 /// assert_eq!(
372 /// query.to_string(MysqlQueryBuilder),
373 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE 'What!' = 'Nothing' AND `id` = 1"#
374 /// );
375 /// assert_eq!(
376 /// query.to_string(PostgresQueryBuilder),
377 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE 'What!' = 'Nothing' AND "id" = 1"#
378 /// );
379 /// assert_eq!(
380 /// query.to_string(SqliteQueryBuilder),
381 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE 'What!' = 'Nothing' AND "id" = 1"#
382 /// );
383 /// ```
384 ///
385 /// Note how you should express a string being a literal vs an identifier.
386 ///
387 /// ```
388 /// use sea_query::{tests_cfg::*, *};
389 ///
390 /// let query = Query::select()
391 /// .column(Char::Character)
392 /// .from(Char::Table)
393 /// .and_where(Expr::col("name").eq("Something"))
394 /// .to_owned();
395 ///
396 /// assert_eq!(
397 /// query.to_string(MysqlQueryBuilder),
398 /// r#"SELECT `character` FROM `character` WHERE `name` = 'Something'"#
399 /// );
400 /// assert_eq!(
401 /// query.to_string(PostgresQueryBuilder),
402 /// r#"SELECT "character" FROM "character" WHERE "name" = 'Something'"#
403 /// );
404 /// assert_eq!(
405 /// query.to_string(SqliteQueryBuilder),
406 /// r#"SELECT "character" FROM "character" WHERE "name" = 'Something'"#
407 /// );
408 /// ```
409 fn eq<R>(self, right: R) -> Expr
410 where
411 R: Into<Expr>,
412 {
413 self.binary(BinOper::Equal, right)
414 }
415
416 /// Express a equal expression between two table columns,
417 /// you will mainly use this to relate identical value between two table columns.
418 ///
419 /// # Examples
420 ///
421 /// ```
422 /// use sea_query::{*, tests_cfg::*};
423 ///
424 /// let query = Query::select()
425 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
426 /// .from(Char::Table)
427 /// .and_where((Char::Table, Char::FontId).into_column_ref().equals((Font::Table, Font::Id)))
428 /// .to_owned();
429 ///
430 /// assert_eq!(
431 /// query.to_string(MysqlQueryBuilder),
432 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE `character`.`font_id` = `font`.`id`"#
433 /// );
434 /// assert_eq!(
435 /// query.to_string(PostgresQueryBuilder),
436 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "character"."font_id" = "font"."id""#
437 /// );
438 /// assert_eq!(
439 /// query.to_string(SqliteQueryBuilder),
440 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "character"."font_id" = "font"."id""#
441 /// );
442 /// ```
443 fn equals<C>(self, col: C) -> Expr
444 where
445 C: IntoColumnRef,
446 {
447 self.binary(BinOper::Equal, col.into_column_ref())
448 }
449
450 /// Express a greater than (`>`) expression.
451 ///
452 /// # Examples
453 ///
454 /// ```
455 /// use sea_query::{tests_cfg::*, *};
456 ///
457 /// let query = Query::select()
458 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
459 /// .from(Char::Table)
460 /// .and_where((Char::Table, Char::SizeW).into_column_ref().gt(2))
461 /// .to_owned();
462 ///
463 /// assert_eq!(
464 /// query.to_string(MysqlQueryBuilder),
465 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE `character`.`size_w` > 2"#
466 /// );
467 /// assert_eq!(
468 /// query.to_string(PostgresQueryBuilder),
469 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "character"."size_w" > 2"#
470 /// );
471 /// assert_eq!(
472 /// query.to_string(SqliteQueryBuilder),
473 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "character"."size_w" > 2"#
474 /// );
475 /// ```
476 fn gt<R>(self, right: R) -> Expr
477 where
478 R: Into<Expr>,
479 {
480 self.binary(BinOper::GreaterThan, right)
481 }
482
483 /// Express a greater than or equal (`>=`) expression.
484 ///
485 /// # Examples
486 ///
487 /// ```
488 /// use sea_query::{tests_cfg::*, *};
489 ///
490 /// let query = Query::select()
491 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
492 /// .from(Char::Table)
493 /// .and_where((Char::Table, Char::SizeW).into_column_ref().gte(2))
494 /// .to_owned();
495 ///
496 /// assert_eq!(
497 /// query.to_string(MysqlQueryBuilder),
498 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE `character`.`size_w` >= 2"#
499 /// );
500 /// assert_eq!(
501 /// query.to_string(PostgresQueryBuilder),
502 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "character"."size_w" >= 2"#
503 /// );
504 /// assert_eq!(
505 /// query.to_string(SqliteQueryBuilder),
506 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "character"."size_w" >= 2"#
507 /// );
508 /// ```
509 fn gte<R>(self, right: R) -> Expr
510 where
511 R: Into<Expr>,
512 {
513 self.binary(BinOper::GreaterThanOrEqual, right)
514 }
515
516 /// Express a `IN` sub-query expression.
517 ///
518 /// # Examples
519 ///
520 /// ```
521 /// use sea_query::{*, tests_cfg::*};
522 ///
523 /// let query = Query::select()
524 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
525 /// .from(Char::Table)
526 /// .and_where(Char::SizeW.into_column_ref().in_subquery(
527 /// Query::select()
528 /// .expr(Expr::cust("3 + 2 * 2"))
529 /// .take()
530 /// ))
531 /// .to_owned();
532 ///
533 /// assert_eq!(
534 /// query.to_string(MysqlQueryBuilder),
535 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE `size_w` IN (SELECT 3 + 2 * 2)"#
536 /// );
537 /// assert_eq!(
538 /// query.to_string(PostgresQueryBuilder),
539 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "size_w" IN (SELECT 3 + 2 * 2)"#
540 /// );
541 /// assert_eq!(
542 /// query.to_string(SqliteQueryBuilder),
543 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "size_w" IN (SELECT 3 + 2 * 2)"#
544 /// );
545 /// ```
546 fn in_subquery(self, sel: SelectStatement) -> Expr {
547 self.binary(BinOper::In, Expr::SubQuery(None, Box::new(sel.into())))
548 }
549
550 /// Express a `IN` sub expression.
551 ///
552 /// # Examples
553 ///
554 /// ```
555 /// use sea_query::{*, tests_cfg::*};
556 ///
557 /// let query = Query::select()
558 /// .columns([Char::Character, Char::FontId])
559 /// .from(Char::Table)
560 /// .and_where(
561 /// Expr::tuple([
562 /// Expr::col(Char::Character).into(),
563 /// Expr::col(Char::FontId).into(),
564 /// ]).in_tuples([(1, String::from("1")), (2, String::from("2"))])
565 /// )
566 /// .to_owned();
567 ///
568 /// assert_eq!(
569 /// query.to_string(MysqlQueryBuilder),
570 /// r#"SELECT `character`, `font_id` FROM `character` WHERE (`character`, `font_id`) IN ((1, '1'), (2, '2'))"#
571 /// );
572 ///
573 /// assert_eq!(
574 /// query.to_string(PostgresQueryBuilder),
575 /// r#"SELECT "character", "font_id" FROM "character" WHERE ("character", "font_id") IN ((1, '1'), (2, '2'))"#
576 /// );
577 ///
578 /// assert_eq!(
579 /// query.to_string(SqliteQueryBuilder),
580 /// r#"SELECT "character", "font_id" FROM "character" WHERE ("character", "font_id") IN ((1, '1'), (2, '2'))"#
581 /// );
582 /// ```
583 fn in_tuples<V, I>(self, v: I) -> Expr
584 where
585 V: IntoValueTuple,
586 I: IntoIterator<Item = V>,
587 {
588 self.binary(
589 BinOper::In,
590 Expr::Tuple(
591 v.into_iter()
592 .map(|m| Expr::Values(m.into_value_tuple().into_iter().collect()))
593 .collect(),
594 ),
595 )
596 }
597
598 /// Express a `IS` expression.
599 ///
600 /// # Examples
601 ///
602 /// ```
603 /// use sea_query::{*, tests_cfg::*};
604 ///
605 /// let query = Query::select()
606 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
607 /// .from(Char::Table)
608 /// .and_where((Char::Table, Char::Ascii).into_column_ref().is(true))
609 /// .to_owned();
610 ///
611 /// assert_eq!(
612 /// query.to_string(MysqlQueryBuilder),
613 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE `character`.`ascii` IS TRUE"#
614 /// );
615 /// assert_eq!(
616 /// query.to_string(PostgresQueryBuilder),
617 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "character"."ascii" IS TRUE"#
618 /// );
619 /// assert_eq!(
620 /// query.to_string(SqliteQueryBuilder),
621 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "character"."ascii" IS TRUE"#
622 /// );
623 /// ```
624 fn is<R>(self, right: R) -> Expr
625 where
626 R: Into<Expr>,
627 {
628 self.binary(BinOper::Is, right)
629 }
630
631 /// Express a `IN` expression.
632 ///
633 /// # Examples
634 ///
635 /// ```
636 /// use sea_query::{tests_cfg::*, *};
637 ///
638 /// let query = Query::select()
639 /// .columns([Char::Id])
640 /// .from(Char::Table)
641 /// .and_where(
642 /// (Char::Table, Char::SizeW)
643 /// .into_column_ref()
644 /// .is_in([1, 2, 3]),
645 /// )
646 /// .to_owned();
647 ///
648 /// assert_eq!(
649 /// query.to_string(MysqlQueryBuilder),
650 /// r#"SELECT `id` FROM `character` WHERE `character`.`size_w` IN (1, 2, 3)"#
651 /// );
652 /// assert_eq!(
653 /// query.to_string(PostgresQueryBuilder),
654 /// r#"SELECT "id" FROM "character" WHERE "character"."size_w" IN (1, 2, 3)"#
655 /// );
656 /// assert_eq!(
657 /// query.to_string(SqliteQueryBuilder),
658 /// r#"SELECT "id" FROM "character" WHERE "character"."size_w" IN (1, 2, 3)"#
659 /// );
660 /// ```
661 ///
662 /// The same query can be constructed using the `raw_query!` macro.
663 ///
664 /// ```
665 /// use sea_query::Values;
666 ///
667 /// let ids: Vec<i32> = vec![1, 2, 3];
668 /// let query = sea_query::raw_query!(
669 /// SqliteQueryBuilder,
670 /// r#"SELECT "id" FROM "character" WHERE "character"."size_w" IN ({..ids})"#
671 /// );
672 ///
673 /// assert_eq!(
674 /// query.sql,
675 /// r#"SELECT "id" FROM "character" WHERE "character"."size_w" IN (?, ?, ?)"#
676 /// );
677 /// assert_eq!(query.values, Values(vec![1.into(), 2.into(), 3.into()]));
678 /// ```
679 ///
680 /// Empty value list is converted to an always false expression due to SQL syntax.
681 ///
682 /// ```
683 /// use sea_query::{tests_cfg::*, *};
684 ///
685 /// let query = Query::select()
686 /// .columns([Char::Id])
687 /// .from(Char::Table)
688 /// .and_where(
689 /// (Char::Table, Char::SizeW)
690 /// .into_column_ref()
691 /// .is_in(Vec::<u8>::new()),
692 /// )
693 /// .to_owned();
694 ///
695 /// assert_eq!(
696 /// query.to_string(MysqlQueryBuilder),
697 /// r#"SELECT `id` FROM `character` WHERE 1 = 2"#
698 /// );
699 /// assert_eq!(
700 /// query.to_string(PostgresQueryBuilder),
701 /// r#"SELECT "id" FROM "character" WHERE 1 = 2"#
702 /// );
703 /// assert_eq!(
704 /// query.to_string(SqliteQueryBuilder),
705 /// r#"SELECT "id" FROM "character" WHERE 1 = 2"#
706 /// );
707 /// ```
708 #[allow(clippy::wrong_self_convention)]
709 fn is_in<V, I>(self, v: I) -> Expr
710 where
711 V: Into<Expr>,
712 I: IntoIterator<Item = V>,
713 {
714 self.binary(
715 BinOper::In,
716 Expr::Tuple(v.into_iter().map(|v| v.into()).collect()),
717 )
718 }
719
720 /// Express a `IS NOT` expression.
721 ///
722 /// # Examples
723 ///
724 /// ```
725 /// use sea_query::{*, tests_cfg::*};
726 ///
727 /// let query = Query::select()
728 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
729 /// .from(Char::Table)
730 /// .and_where((Char::Table, Char::Ascii).into_column_ref().is_not(true))
731 /// .to_owned();
732 ///
733 /// assert_eq!(
734 /// query.to_string(MysqlQueryBuilder),
735 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE `character`.`ascii` IS NOT TRUE"#
736 /// );
737 /// assert_eq!(
738 /// query.to_string(PostgresQueryBuilder),
739 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "character"."ascii" IS NOT TRUE"#
740 /// );
741 /// assert_eq!(
742 /// query.to_string(SqliteQueryBuilder),
743 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "character"."ascii" IS NOT TRUE"#
744 /// );
745 /// ```
746 #[allow(clippy::wrong_self_convention)]
747 fn is_not<R>(self, right: R) -> Expr
748 where
749 R: Into<Expr>,
750 {
751 self.binary(BinOper::IsNot, right)
752 }
753
754 /// Express a `NOT IN` expression.
755 ///
756 /// # Examples
757 ///
758 /// ```
759 /// use sea_query::{tests_cfg::*, *};
760 ///
761 /// let query = Query::select()
762 /// .columns([Char::Id])
763 /// .from(Char::Table)
764 /// .and_where(
765 /// (Char::Table, Char::SizeW)
766 /// .into_column_ref()
767 /// .is_not_in([1, 2, 3]),
768 /// )
769 /// .to_owned();
770 ///
771 /// assert_eq!(
772 /// query.to_string(MysqlQueryBuilder),
773 /// r#"SELECT `id` FROM `character` WHERE `character`.`size_w` NOT IN (1, 2, 3)"#
774 /// );
775 /// assert_eq!(
776 /// query.to_string(PostgresQueryBuilder),
777 /// r#"SELECT "id" FROM "character" WHERE "character"."size_w" NOT IN (1, 2, 3)"#
778 /// );
779 /// assert_eq!(
780 /// query.to_string(SqliteQueryBuilder),
781 /// r#"SELECT "id" FROM "character" WHERE "character"."size_w" NOT IN (1, 2, 3)"#
782 /// );
783 /// ```
784 /// Empty value list
785 /// ```
786 /// use sea_query::{tests_cfg::*, *};
787 ///
788 /// let query = Query::select()
789 /// .columns([Char::Id])
790 /// .from(Char::Table)
791 /// .and_where(
792 /// (Char::Table, Char::SizeW)
793 /// .into_column_ref()
794 /// .is_not_in(Vec::<u8>::new()),
795 /// )
796 /// .to_owned();
797 ///
798 /// assert_eq!(
799 /// query.to_string(MysqlQueryBuilder),
800 /// r#"SELECT `id` FROM `character` WHERE 1 = 1"#
801 /// );
802 /// assert_eq!(
803 /// query.to_string(PostgresQueryBuilder),
804 /// r#"SELECT "id" FROM "character" WHERE 1 = 1"#
805 /// );
806 /// assert_eq!(
807 /// query.to_string(SqliteQueryBuilder),
808 /// r#"SELECT "id" FROM "character" WHERE 1 = 1"#
809 /// );
810 /// ```
811 #[allow(clippy::wrong_self_convention)]
812 fn is_not_in<V, I>(self, v: I) -> Expr
813 where
814 V: Into<Expr>,
815 I: IntoIterator<Item = V>,
816 {
817 self.binary(
818 BinOper::NotIn,
819 Expr::Tuple(v.into_iter().map(|v| v.into()).collect()),
820 )
821 }
822
823 /// Express a `IS NOT NULL` expression.
824 ///
825 /// # Examples
826 ///
827 /// ```
828 /// use sea_query::{*, tests_cfg::*};
829 ///
830 /// let query = Query::select()
831 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
832 /// .from(Char::Table)
833 /// .and_where((Char::Table, Char::SizeW).into_column_ref().is_not_null())
834 /// .to_owned();
835 ///
836 /// assert_eq!(
837 /// query.to_string(MysqlQueryBuilder),
838 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE `character`.`size_w` IS NOT NULL"#
839 /// );
840 /// assert_eq!(
841 /// query.to_string(PostgresQueryBuilder),
842 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "character"."size_w" IS NOT NULL"#
843 /// );
844 /// assert_eq!(
845 /// query.to_string(SqliteQueryBuilder),
846 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "character"."size_w" IS NOT NULL"#
847 /// );
848 /// ```
849 #[allow(clippy::wrong_self_convention)]
850 fn is_not_null(self) -> Expr {
851 self.binary(BinOper::IsNot, Keyword::Null)
852 }
853
854 /// Express a `IS NULL` expression.
855 ///
856 /// # Examples
857 ///
858 /// ```
859 /// use sea_query::{*, tests_cfg::*};
860 ///
861 /// let query = Query::select()
862 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
863 /// .from(Char::Table)
864 /// .and_where((Char::Table, Char::SizeW).into_column_ref().is_null())
865 /// .to_owned();
866 ///
867 /// assert_eq!(
868 /// query.to_string(MysqlQueryBuilder),
869 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE `character`.`size_w` IS NULL"#
870 /// );
871 /// assert_eq!(
872 /// query.to_string(PostgresQueryBuilder),
873 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "character"."size_w" IS NULL"#
874 /// );
875 /// assert_eq!(
876 /// query.to_string(SqliteQueryBuilder),
877 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "character"."size_w" IS NULL"#
878 /// );
879 /// ```
880 #[allow(clippy::wrong_self_convention)]
881 fn is_null(self) -> Expr {
882 self.binary(BinOper::Is, Keyword::Null)
883 }
884
885 /// Express a bitwise left shift.
886 ///
887 /// # Examples
888 ///
889 /// ```
890 /// use sea_query::{tests_cfg::*, *};
891 ///
892 /// let query = Query::select()
893 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
894 /// .from(Char::Table)
895 /// .and_where(1.left_shift(1).eq(2))
896 /// .to_owned();
897 ///
898 /// assert_eq!(
899 /// query.to_string(MysqlQueryBuilder),
900 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE 1 << 1 = 2"#
901 /// );
902 /// assert_eq!(
903 /// query.to_string(PostgresQueryBuilder),
904 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE 1 << 1 = 2"#
905 /// );
906 /// assert_eq!(
907 /// query.to_string(SqliteQueryBuilder),
908 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE 1 << 1 = 2"#
909 /// );
910 /// ```
911 fn left_shift<R>(self, right: R) -> Expr
912 where
913 R: Into<Expr>,
914 {
915 self.binary(BinOper::LShift, right)
916 }
917
918 /// Express a `LIKE` expression.
919 ///
920 /// # Examples
921 ///
922 /// ```
923 /// use sea_query::{*, tests_cfg::*};
924 ///
925 /// let query = Query::select()
926 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
927 /// .from(Char::Table)
928 /// .and_where((Char::Table, Char::Character).into_column_ref().like("Ours'%"))
929 /// .to_owned();
930 ///
931 /// assert_eq!(
932 /// query.to_string(MysqlQueryBuilder),
933 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE `character`.`character` LIKE 'Ours\'%'"#
934 /// );
935 /// assert_eq!(
936 /// query.to_string(PostgresQueryBuilder),
937 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "character"."character" LIKE E'Ours\'%'"#
938 /// );
939 /// assert_eq!(
940 /// query.to_string(SqliteQueryBuilder),
941 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "character"."character" LIKE 'Ours''%'"#
942 /// );
943 /// ```
944 ///
945 /// Like with ESCAPE
946 ///
947 /// ```
948 /// use sea_query::{*, tests_cfg::*};
949 ///
950 /// let query = Query::select()
951 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
952 /// .from(Char::Table)
953 /// .and_where((Char::Table, Char::Character).into_column_ref().like(LikeExpr::new(r"|_Our|_").escape('|')))
954 /// .to_owned();
955 ///
956 /// assert_eq!(
957 /// query.to_string(MysqlQueryBuilder),
958 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE `character`.`character` LIKE '|_Our|_' ESCAPE '|'"#
959 /// );
960 /// assert_eq!(
961 /// query.to_string(PostgresQueryBuilder),
962 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "character"."character" LIKE '|_Our|_' ESCAPE '|'"#
963 /// );
964 /// assert_eq!(
965 /// query.to_string(SqliteQueryBuilder),
966 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "character"."character" LIKE '|_Our|_' ESCAPE '|'"#
967 /// );
968 /// ```
969 fn like<L>(self, like: L) -> Expr
970 where
971 L: IntoLikeExpr,
972 {
973 self.binary(BinOper::Like, like.into_like_expr())
974 }
975
976 /// Express a less than (`<`) expression.
977 ///
978 /// # Examples
979 ///
980 /// ```
981 /// use sea_query::{tests_cfg::*, *};
982 ///
983 /// let query = Query::select()
984 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
985 /// .from(Char::Table)
986 /// .and_where((Char::Table, Char::SizeW).into_column_ref().lt(2))
987 /// .to_owned();
988 ///
989 /// assert_eq!(
990 /// query.to_string(MysqlQueryBuilder),
991 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE `character`.`size_w` < 2"#
992 /// );
993 /// assert_eq!(
994 /// query.to_string(PostgresQueryBuilder),
995 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "character"."size_w" < 2"#
996 /// );
997 /// assert_eq!(
998 /// query.to_string(SqliteQueryBuilder),
999 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "character"."size_w" < 2"#
1000 /// );
1001 /// ```
1002 fn lt<R>(self, right: R) -> Expr
1003 where
1004 R: Into<Expr>,
1005 {
1006 self.binary(BinOper::SmallerThan, right)
1007 }
1008
1009 /// Express a less than or equal (`<=`) expression.
1010 ///
1011 /// # Examples
1012 ///
1013 /// ```
1014 /// use sea_query::{tests_cfg::*, *};
1015 ///
1016 /// let query = Query::select()
1017 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
1018 /// .from(Char::Table)
1019 /// .and_where((Char::Table, Char::SizeW).into_column_ref().lte(2))
1020 /// .to_owned();
1021 ///
1022 /// assert_eq!(
1023 /// query.to_string(MysqlQueryBuilder),
1024 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE `character`.`size_w` <= 2"#
1025 /// );
1026 /// assert_eq!(
1027 /// query.to_string(PostgresQueryBuilder),
1028 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "character"."size_w" <= 2"#
1029 /// );
1030 /// assert_eq!(
1031 /// query.to_string(SqliteQueryBuilder),
1032 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "character"."size_w" <= 2"#
1033 /// );
1034 /// ```
1035 fn lte<R>(self, right: R) -> Expr
1036 where
1037 R: Into<Expr>,
1038 {
1039 self.binary(BinOper::SmallerThanOrEqual, right)
1040 }
1041
1042 /// Express an arithmetic modulo operation.
1043 ///
1044 /// # Examples
1045 ///
1046 /// ```
1047 /// use sea_query::{tests_cfg::*, *};
1048 ///
1049 /// let query = Query::select()
1050 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
1051 /// .from(Char::Table)
1052 /// .and_where(1.modulo(1).eq(2))
1053 /// .to_owned();
1054 ///
1055 /// assert_eq!(
1056 /// query.to_string(MysqlQueryBuilder),
1057 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE 1 % 1 = 2"#
1058 /// );
1059 /// assert_eq!(
1060 /// query.to_string(PostgresQueryBuilder),
1061 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE 1 % 1 = 2"#
1062 /// );
1063 /// assert_eq!(
1064 /// query.to_string(SqliteQueryBuilder),
1065 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE 1 % 1 = 2"#
1066 /// );
1067 /// ```
1068 fn modulo<R>(self, right: R) -> Expr
1069 where
1070 R: Into<Expr>,
1071 {
1072 self.binary(BinOper::Mod, right)
1073 }
1074
1075 /// Express an arithmetic multiplication operation.
1076 ///
1077 /// # Examples
1078 ///
1079 /// ```
1080 /// use sea_query::{tests_cfg::*, *};
1081 ///
1082 /// let query = Query::select()
1083 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
1084 /// .from(Char::Table)
1085 /// .and_where(1.mul(1).eq(2))
1086 /// .to_owned();
1087 ///
1088 /// assert_eq!(
1089 /// query.to_string(MysqlQueryBuilder),
1090 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE 1 * 1 = 2"#
1091 /// );
1092 /// assert_eq!(
1093 /// query.to_string(PostgresQueryBuilder),
1094 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE 1 * 1 = 2"#
1095 /// );
1096 /// assert_eq!(
1097 /// query.to_string(SqliteQueryBuilder),
1098 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE 1 * 1 = 2"#
1099 /// );
1100 /// ```
1101 fn mul<R>(self, right: R) -> Expr
1102 where
1103 R: Into<Expr>,
1104 {
1105 self.binary(BinOper::Mul, right)
1106 }
1107
1108 /// Express a not equal (`<>`) expression.
1109 ///
1110 /// # Examples
1111 ///
1112 /// ```
1113 /// use sea_query::{*, tests_cfg::*};
1114 ///
1115 /// let query = Query::select()
1116 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
1117 /// .from(Char::Table)
1118 /// // Sometimes, you'll have to qualify the call because of conflicting std traits.
1119 /// .and_where(ExprTrait::ne("Morning", "Good"))
1120 /// .and_where(Char::Id.into_column_ref().ne(1))
1121 /// .to_owned();
1122 ///
1123 /// assert_eq!(
1124 /// query.to_string(MysqlQueryBuilder),
1125 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE 'Morning' <> 'Good' AND `id` <> 1"#
1126 /// );
1127 /// assert_eq!(
1128 /// query.to_string(PostgresQueryBuilder),
1129 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE 'Morning' <> 'Good' AND "id" <> 1"#
1130 /// );
1131 /// assert_eq!(
1132 /// query.to_string(SqliteQueryBuilder),
1133 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE 'Morning' <> 'Good' AND "id" <> 1"#
1134 /// );
1135 /// ```
1136 fn ne<R>(self, right: R) -> Expr
1137 where
1138 R: Into<Expr>,
1139 {
1140 self.binary(BinOper::NotEqual, right)
1141 }
1142
1143 /// Negates an expression with `NOT`.
1144 ///
1145 /// # Examples
1146 ///
1147 /// ```
1148 /// use sea_query::{*, tests_cfg::*};
1149 ///
1150 /// let query = Query::select()
1151 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
1152 /// .from(Char::Table)
1153 /// .and_where(Expr::col((Char::Table, Char::SizeW)).is_null().not())
1154 /// .to_owned();
1155 ///
1156 /// assert_eq!(
1157 /// query.to_string(MysqlQueryBuilder),
1158 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE NOT `character`.`size_w` IS NULL"#
1159 /// );
1160 /// assert_eq!(
1161 /// query.to_string(PostgresQueryBuilder),
1162 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE NOT "character"."size_w" IS NULL"#
1163 /// );
1164 /// assert_eq!(
1165 /// query.to_string(SqliteQueryBuilder),
1166 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE NOT "character"."size_w" IS NULL"#
1167 /// );
1168 /// ```
1169 fn not(self) -> Expr {
1170 self.unary(UnOper::Not)
1171 }
1172
1173 /// Express a `NOT BETWEEN` expression.
1174 ///
1175 /// # Examples
1176 ///
1177 /// ```
1178 /// use sea_query::{*, tests_cfg::*};
1179 ///
1180 /// let query = Query::select()
1181 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
1182 /// .from(Char::Table)
1183 /// .and_where((Char::Table, Char::SizeW).into_column_ref().not_between(1, 10))
1184 /// .to_owned();
1185 ///
1186 /// assert_eq!(
1187 /// query.to_string(MysqlQueryBuilder),
1188 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE `character`.`size_w` NOT BETWEEN 1 AND 10"#
1189 /// );
1190 /// assert_eq!(
1191 /// query.to_string(PostgresQueryBuilder),
1192 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "character"."size_w" NOT BETWEEN 1 AND 10"#
1193 /// );
1194 /// assert_eq!(
1195 /// query.to_string(SqliteQueryBuilder),
1196 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "character"."size_w" NOT BETWEEN 1 AND 10"#
1197 /// );
1198 /// ```
1199 fn not_between<A, B>(self, a: A, b: B) -> Expr
1200 where
1201 A: Into<Expr>,
1202 B: Into<Expr>,
1203 {
1204 self.binary(
1205 BinOper::NotBetween,
1206 Expr::Binary(Box::new(a.into()), BinOper::And, Box::new(b.into())),
1207 )
1208 }
1209
1210 /// Express a not equal expression between two table columns,
1211 /// you will mainly use this to relate identical value between two table columns.
1212 ///
1213 /// # Examples
1214 ///
1215 /// ```
1216 /// use sea_query::{*, tests_cfg::*};
1217 ///
1218 /// let query = Query::select()
1219 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
1220 /// .from(Char::Table)
1221 /// .and_where((Char::Table, Char::FontId).into_column_ref().not_equals((Font::Table, Font::Id)))
1222 /// .to_owned();
1223 ///
1224 /// assert_eq!(
1225 /// query.to_string(MysqlQueryBuilder),
1226 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE `character`.`font_id` <> `font`.`id`"#
1227 /// );
1228 /// assert_eq!(
1229 /// query.to_string(PostgresQueryBuilder),
1230 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "character"."font_id" <> "font"."id""#
1231 /// );
1232 /// assert_eq!(
1233 /// query.to_string(SqliteQueryBuilder),
1234 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "character"."font_id" <> "font"."id""#
1235 /// );
1236 /// ```
1237 fn not_equals<C>(self, col: C) -> Expr
1238 where
1239 C: IntoColumnRef,
1240 {
1241 self.binary(BinOper::NotEqual, col.into_column_ref())
1242 }
1243
1244 /// Express a `NOT IN` sub-query expression.
1245 ///
1246 /// # Examples
1247 ///
1248 /// ```
1249 /// use sea_query::{*, tests_cfg::*};
1250 ///
1251 /// let query = Query::select()
1252 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
1253 /// .from(Char::Table)
1254 /// .and_where(Char::SizeW.into_column_ref().not_in_subquery(
1255 /// Query::select()
1256 /// .expr(Expr::cust("3 + 2 * 2"))
1257 /// .take()
1258 /// ))
1259 /// .to_owned();
1260 ///
1261 /// assert_eq!(
1262 /// query.to_string(MysqlQueryBuilder),
1263 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE `size_w` NOT IN (SELECT 3 + 2 * 2)"#
1264 /// );
1265 /// assert_eq!(
1266 /// query.to_string(PostgresQueryBuilder),
1267 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "size_w" NOT IN (SELECT 3 + 2 * 2)"#
1268 /// );
1269 /// assert_eq!(
1270 /// query.to_string(SqliteQueryBuilder),
1271 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "size_w" NOT IN (SELECT 3 + 2 * 2)"#
1272 /// );
1273 /// ```
1274 fn not_in_subquery(self, sel: SelectStatement) -> Expr {
1275 self.binary(BinOper::NotIn, Expr::SubQuery(None, Box::new(sel.into())))
1276 }
1277
1278 /// Express a `NOT LIKE` expression.
1279 ///
1280 /// # Examples
1281 ///
1282 /// ```
1283 /// use sea_query::{*, tests_cfg::*};
1284 ///
1285 /// let query = Query::select()
1286 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
1287 /// .from(Char::Table)
1288 /// .and_where((Char::Table, Char::Character).into_column_ref().not_like("Ours'%"))
1289 /// .to_owned();
1290 ///
1291 /// assert_eq!(
1292 /// query.to_string(MysqlQueryBuilder),
1293 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE `character`.`character` NOT LIKE 'Ours\'%'"#
1294 /// );
1295 /// assert_eq!(
1296 /// query.to_string(PostgresQueryBuilder),
1297 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "character"."character" NOT LIKE E'Ours\'%'"#
1298 /// );
1299 /// assert_eq!(
1300 /// query.to_string(SqliteQueryBuilder),
1301 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "character"."character" NOT LIKE 'Ours''%'"#
1302 /// );
1303 /// ```
1304 fn not_like<L>(self, like: L) -> Expr
1305 where
1306 L: IntoLikeExpr,
1307 {
1308 self.binary(BinOper::NotLike, like.into_like_expr())
1309 }
1310
1311 /// Express a logical `OR` operation.
1312 ///
1313 /// # Examples
1314 ///
1315 /// ```
1316 /// use sea_query::{tests_cfg::*, *};
1317 ///
1318 /// let query = Query::select()
1319 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
1320 /// .from(Char::Table)
1321 /// .and_where(false.or(true))
1322 /// .to_owned();
1323 ///
1324 /// assert_eq!(
1325 /// query.to_string(MysqlQueryBuilder),
1326 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE FALSE OR TRUE"#
1327 /// );
1328 /// assert_eq!(
1329 /// query.to_string(PostgresQueryBuilder),
1330 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE FALSE OR TRUE"#
1331 /// );
1332 /// assert_eq!(
1333 /// query.to_string(SqliteQueryBuilder),
1334 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE FALSE OR TRUE"#
1335 /// );
1336 /// ```
1337 fn or<R>(self, right: R) -> Expr
1338 where
1339 R: Into<Expr>,
1340 {
1341 self.binary(BinOper::Or, right)
1342 }
1343
1344 /// Express a bitwise right shift.
1345 ///
1346 /// # Examples
1347 ///
1348 /// ```
1349 /// use sea_query::{tests_cfg::*, *};
1350 ///
1351 /// let query = Query::select()
1352 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
1353 /// .from(Char::Table)
1354 /// .and_where(1.right_shift(1).eq(2))
1355 /// .to_owned();
1356 ///
1357 /// assert_eq!(
1358 /// query.to_string(MysqlQueryBuilder),
1359 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE 1 >> 1 = 2"#
1360 /// );
1361 /// assert_eq!(
1362 /// query.to_string(PostgresQueryBuilder),
1363 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE 1 >> 1 = 2"#
1364 /// );
1365 /// assert_eq!(
1366 /// query.to_string(SqliteQueryBuilder),
1367 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE 1 >> 1 = 2"#
1368 /// );
1369 /// ```
1370 fn right_shift<R>(self, right: R) -> Expr
1371 where
1372 R: Into<Expr>,
1373 {
1374 self.binary(BinOper::RShift, right)
1375 }
1376
1377 /// Express an arithmetic subtraction operation.
1378 ///
1379 /// # Examples
1380 ///
1381 /// ```
1382 /// use sea_query::{tests_cfg::*, *};
1383 ///
1384 /// let query = Query::select()
1385 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
1386 /// .from(Char::Table)
1387 /// .and_where(1.sub(1).eq(2))
1388 /// .to_owned();
1389 ///
1390 /// assert_eq!(
1391 /// query.to_string(MysqlQueryBuilder),
1392 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE 1 - 1 = 2"#
1393 /// );
1394 /// assert_eq!(
1395 /// query.to_string(PostgresQueryBuilder),
1396 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE 1 - 1 = 2"#
1397 /// );
1398 /// assert_eq!(
1399 /// query.to_string(SqliteQueryBuilder),
1400 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE 1 - 1 = 2"#
1401 /// );
1402 /// ```
1403 fn sub<R>(self, right: R) -> Expr
1404 where
1405 R: Into<Expr>,
1406 {
1407 self.binary(BinOper::Sub, right)
1408 }
1409
1410 /// Apply any unary operator to the expression.
1411 ///
1412 /// # Examples
1413 ///
1414 /// ```
1415 /// use sea_query::{*, tests_cfg::*};
1416 ///
1417 /// let query = Query::select()
1418 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
1419 /// .from(Char::Table)
1420 /// .and_where(Expr::col((Char::Table, Char::SizeW)).is_null().unary(UnOper::Not))
1421 /// .to_owned();
1422 ///
1423 /// assert_eq!(
1424 /// query.to_string(MysqlQueryBuilder),
1425 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE NOT `character`.`size_w` IS NULL"#
1426 /// );
1427 /// assert_eq!(
1428 /// query.to_string(PostgresQueryBuilder),
1429 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE NOT "character"."size_w" IS NULL"#
1430 /// );
1431 /// assert_eq!(
1432 /// query.to_string(SqliteQueryBuilder),
1433 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE NOT "character"."size_w" IS NULL"#
1434 /// );
1435 /// ```
1436 fn unary(self, o: UnOper) -> Expr;
1437
1438 /// Express a bitwise AND operation.
1439 ///
1440 /// # Examples
1441 ///
1442 /// ```
1443 /// use sea_query::{tests_cfg::*, *};
1444 ///
1445 /// let query = Query::select().expr(1.bit_and(2).eq(3)).to_owned();
1446 ///
1447 /// assert_eq!(
1448 /// query.to_string(PostgresQueryBuilder),
1449 /// r#"SELECT (1 & 2) = 3"#
1450 /// );
1451 ///
1452 /// let query = Query::select()
1453 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
1454 /// .from(Char::Table)
1455 /// .and_where(1.bit_and(1).eq(1))
1456 /// .to_owned();
1457 ///
1458 /// assert_eq!(
1459 /// query.to_string(MysqlQueryBuilder),
1460 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE (1 & 1) = 1"#
1461 /// );
1462 /// assert_eq!(
1463 /// query.to_string(PostgresQueryBuilder),
1464 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE (1 & 1) = 1"#
1465 /// );
1466 /// assert_eq!(
1467 /// query.to_string(SqliteQueryBuilder),
1468 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE (1 & 1) = 1"#
1469 /// );
1470 /// ```
1471 fn bit_and<R>(self, right: R) -> Expr
1472 where
1473 R: Into<Expr>,
1474 {
1475 self.binary(BinOper::BitAnd, right)
1476 }
1477
1478 /// Express a bitwise OR operation.
1479 ///
1480 /// # Examples
1481 ///
1482 /// ```
1483 /// use sea_query::{tests_cfg::*, *};
1484 ///
1485 /// let query = Query::select()
1486 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
1487 /// .from(Char::Table)
1488 /// .and_where(1.bit_or(1).eq(1))
1489 /// .to_owned();
1490 ///
1491 /// assert_eq!(
1492 /// query.to_string(MysqlQueryBuilder),
1493 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE (1 | 1) = 1"#
1494 /// );
1495 /// assert_eq!(
1496 /// query.to_string(PostgresQueryBuilder),
1497 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE (1 | 1) = 1"#
1498 /// );
1499 /// assert_eq!(
1500 /// query.to_string(SqliteQueryBuilder),
1501 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE (1 | 1) = 1"#
1502 /// );
1503 /// ```
1504 fn bit_or<R>(self, right: R) -> Expr
1505 where
1506 R: Into<Expr>,
1507 {
1508 self.binary(BinOper::BitOr, right)
1509 }
1510}
1511
1512/// This generic implementation covers all expression types,
1513/// including [ColumnRef], [Value], [FunctionCall], [Expr]...
1514impl<T> ExprTrait for T
1515where
1516 T: Into<Expr>,
1517{
1518 fn as_enum<N>(self, type_name: N) -> Expr
1519 where
1520 N: IntoIden,
1521 {
1522 Expr::AsEnum(type_name.into_iden(), Box::new(self.into()))
1523 }
1524
1525 fn binary<O, R>(self, op: O, right: R) -> Expr
1526 where
1527 O: Into<BinOper>,
1528 R: Into<Expr>,
1529 {
1530 Expr::Binary(Box::new(self.into()), op.into(), Box::new(right.into()))
1531 }
1532
1533 fn cast_as<N>(self, type_name: N) -> Expr
1534 where
1535 N: IntoIden,
1536 {
1537 Expr::FunctionCall(Func::cast_as(self, type_name))
1538 }
1539
1540 fn unary(self, op: UnOper) -> Expr {
1541 Expr::Unary(op, Box::new(self.into()))
1542 }
1543}
1544
1545impl Expr {
1546 #[deprecated(since = "0.29.0", note = "Please use the [`Asterisk`]")]
1547 pub fn asterisk() -> Self {
1548 Self::col(Asterisk)
1549 }
1550
1551 /// Express the target column without table prefix.
1552 ///
1553 /// # Examples
1554 ///
1555 /// ```
1556 /// use sea_query::{tests_cfg::*, *};
1557 ///
1558 /// let query = Query::select()
1559 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
1560 /// .from(Char::Table)
1561 /// .and_where(Expr::col(Char::SizeW).eq(1))
1562 /// .to_owned();
1563 ///
1564 /// assert_eq!(
1565 /// query.to_string(MysqlQueryBuilder),
1566 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE `size_w` = 1"#
1567 /// );
1568 /// assert_eq!(
1569 /// query.to_string(PostgresQueryBuilder),
1570 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "size_w" = 1"#
1571 /// );
1572 /// assert_eq!(
1573 /// query.to_string(SqliteQueryBuilder),
1574 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "size_w" = 1"#
1575 /// );
1576 /// ```
1577 ///
1578 /// ```
1579 /// use sea_query::{tests_cfg::*, *};
1580 ///
1581 /// let query = Query::select()
1582 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
1583 /// .from(Char::Table)
1584 /// .and_where(Expr::col((Char::Table, Char::SizeW)).eq(1))
1585 /// .to_owned();
1586 ///
1587 /// assert_eq!(
1588 /// query.to_string(MysqlQueryBuilder),
1589 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE `character`.`size_w` = 1"#
1590 /// );
1591 /// assert_eq!(
1592 /// query.to_string(PostgresQueryBuilder),
1593 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "character"."size_w" = 1"#
1594 /// );
1595 /// assert_eq!(
1596 /// query.to_string(SqliteQueryBuilder),
1597 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "character"."size_w" = 1"#
1598 /// );
1599 /// ```
1600 pub fn col<T>(n: T) -> Self
1601 where
1602 T: IntoColumnRef,
1603 {
1604 Self::Column(n.into_column_ref())
1605 }
1606
1607 /// Express the target column without table prefix, returning a [`Expr`].
1608 ///
1609 /// # Examples
1610 ///
1611 /// ```
1612 /// use sea_query::{tests_cfg::*, *};
1613 ///
1614 /// let query = Query::select()
1615 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
1616 /// .from(Char::Table)
1617 /// .and_where(Expr::column(Char::SizeW).eq(1))
1618 /// .to_owned();
1619 ///
1620 /// assert_eq!(
1621 /// query.to_string(MysqlQueryBuilder),
1622 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE `size_w` = 1"#
1623 /// );
1624 /// assert_eq!(
1625 /// query.to_string(PostgresQueryBuilder),
1626 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "size_w" = 1"#
1627 /// );
1628 /// assert_eq!(
1629 /// query.to_string(SqliteQueryBuilder),
1630 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "size_w" = 1"#
1631 /// );
1632 /// ```
1633 ///
1634 /// ```
1635 /// use sea_query::{tests_cfg::*, *};
1636 ///
1637 /// let query = Query::select()
1638 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
1639 /// .from(Char::Table)
1640 /// .and_where(Expr::column((Char::Table, Char::SizeW)).eq(1))
1641 /// .to_owned();
1642 ///
1643 /// assert_eq!(
1644 /// query.to_string(MysqlQueryBuilder),
1645 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE `character`.`size_w` = 1"#
1646 /// );
1647 /// assert_eq!(
1648 /// query.to_string(PostgresQueryBuilder),
1649 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "character"."size_w" = 1"#
1650 /// );
1651 /// assert_eq!(
1652 /// query.to_string(SqliteQueryBuilder),
1653 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "character"."size_w" = 1"#
1654 /// );
1655 /// ```
1656 pub fn column<T>(n: T) -> Self
1657 where
1658 T: IntoColumnRef,
1659 {
1660 Self::Column(n.into_column_ref())
1661 }
1662
1663 /// Wraps tuple of `Expr`, can be used for tuple comparison
1664 ///
1665 /// # Examples
1666 ///
1667 /// ```
1668 /// use sea_query::{tests_cfg::*, *};
1669 ///
1670 /// let query = Query::select()
1671 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
1672 /// .from(Char::Table)
1673 /// .and_where(
1674 /// Expr::tuple([Expr::col(Char::SizeW).into(), Expr::value(100)])
1675 /// .lt(Expr::tuple([Expr::value(500), Expr::value(100)])))
1676 /// .to_owned();
1677 ///
1678 /// assert_eq!(
1679 /// query.to_string(MysqlQueryBuilder),
1680 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE (`size_w`, 100) < (500, 100)"#
1681 /// );
1682 /// assert_eq!(
1683 /// query.to_string(PostgresQueryBuilder),
1684 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE ("size_w", 100) < (500, 100)"#
1685 /// );
1686 /// assert_eq!(
1687 /// query.to_string(SqliteQueryBuilder),
1688 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE ("size_w", 100) < (500, 100)"#
1689 /// );
1690 /// ```
1691 pub fn tuple<I>(n: I) -> Self
1692 where
1693 I: IntoIterator<Item = Self>,
1694 {
1695 Self::Tuple(n.into_iter().collect::<Vec<Self>>())
1696 }
1697
1698 #[deprecated(since = "0.29.0", note = "Please use the [`Asterisk`]")]
1699 pub fn table_asterisk<T>(t: T) -> Self
1700 where
1701 T: IntoIden,
1702 {
1703 Self::col((t.into_iden(), Asterisk))
1704 }
1705
1706 /// Express a [`Value`], returning a [`Expr`].
1707 ///
1708 /// # Examples
1709 ///
1710 /// ```
1711 /// use sea_query::{tests_cfg::*, *};
1712 ///
1713 /// let query = Query::select()
1714 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
1715 /// .from(Char::Table)
1716 /// .and_where(Expr::val(1).into())
1717 /// .and_where(Expr::val(2.5).into())
1718 /// .and_where(Expr::val("3").into())
1719 /// .to_owned();
1720 ///
1721 /// assert_eq!(
1722 /// query.to_string(MysqlQueryBuilder),
1723 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE 1 AND 2.5 AND '3'"#
1724 /// );
1725 /// assert_eq!(
1726 /// query.to_string(PostgresQueryBuilder),
1727 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE 1 AND 2.5 AND '3'"#
1728 /// );
1729 /// assert_eq!(
1730 /// query.to_string(SqliteQueryBuilder),
1731 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE 1 AND 2.5 AND '3'"#
1732 /// );
1733 /// ```
1734 pub fn val<V>(v: V) -> Self
1735 where
1736 V: Into<Value>,
1737 {
1738 Self::from(v)
1739 }
1740
1741 /// Wrap an expression to perform some operation on it later.
1742 ///
1743 /// Since `sea_query` 0.32.0 (`sea_orm` 1.1.1), **this is not necessary** in most cases!
1744 ///
1745 /// Some SQL operations used to be defined only as inherent methods on [`Expr`].
1746 /// Thus, to use them, you needed to manually convert from other types to [`Expr`].
1747 /// But now these operations are also defined as [`ExprTrait`] methods
1748 /// that can be called directly on any expression type,
1749 ///
1750 /// # Examples
1751 ///
1752 /// ```
1753 /// use sea_query::{tests_cfg::*, *};
1754 ///
1755 /// let query = Query::select()
1756 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
1757 /// .from(Char::Table)
1758 /// // This is the old style, when `Expr::expr` was necessary:
1759 /// .and_where(Expr::expr(Expr::col(Char::SizeW).if_null(0)).gt(2))
1760 /// .to_owned();
1761 ///
1762 /// // But since 0.32.0, this compiles too:
1763 /// let _ = Expr::col(Char::SizeW).if_null(0).gt(2);
1764 ///
1765 /// assert_eq!(
1766 /// query.to_string(MysqlQueryBuilder),
1767 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE IFNULL(`size_w`, 0) > 2"#
1768 /// );
1769 /// assert_eq!(
1770 /// query.to_string(PostgresQueryBuilder),
1771 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE COALESCE("size_w", 0) > 2"#
1772 /// );
1773 /// assert_eq!(
1774 /// query.to_string(SqliteQueryBuilder),
1775 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE IFNULL("size_w", 0) > 2"#
1776 /// );
1777 /// ```
1778 ///
1779 /// ```
1780 /// use sea_query::{tests_cfg::*, *};
1781 ///
1782 /// let query = Query::select()
1783 /// .column(Char::Character)
1784 /// .from(Char::Table)
1785 /// // This is the old style, when `Expr::expr` was necessary:
1786 /// .and_where(Expr::expr(Func::lower(Expr::col(Char::Character))).is_in(["a", "b"]))
1787 /// .to_owned();
1788 ///
1789 /// // But since 0.32.0, this compiles too:
1790 /// let _ = Func::lower(Expr::col(Char::Character)).is_in(["a", "b"]);
1791 ///
1792 /// assert_eq!(
1793 /// query.to_string(MysqlQueryBuilder),
1794 /// r#"SELECT `character` FROM `character` WHERE LOWER(`character`) IN ('a', 'b')"#
1795 /// );
1796 /// assert_eq!(
1797 /// query.to_string(PostgresQueryBuilder),
1798 /// r#"SELECT "character" FROM "character" WHERE LOWER("character") IN ('a', 'b')"#
1799 /// );
1800 /// assert_eq!(
1801 /// query.to_string(SqliteQueryBuilder),
1802 /// r#"SELECT "character" FROM "character" WHERE LOWER("character") IN ('a', 'b')"#
1803 /// );
1804 /// ```
1805 #[allow(clippy::self_named_constructors)]
1806 pub fn expr<T>(expr: T) -> Self
1807 where
1808 T: Into<Self>,
1809 {
1810 expr.into()
1811 }
1812
1813 /// Express a [`Value`], returning a [`Expr`].
1814 ///
1815 /// # Examples
1816 ///
1817 /// ```
1818 /// use sea_query::{tests_cfg::*, *};
1819 ///
1820 /// let query = Query::select()
1821 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
1822 /// .from(Char::Table)
1823 /// .and_where(Expr::value(1))
1824 /// .and_where(Expr::value(2.5))
1825 /// .and_where(Expr::value("3"))
1826 /// .to_owned();
1827 ///
1828 /// assert_eq!(
1829 /// query.to_string(MysqlQueryBuilder),
1830 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE 1 AND 2.5 AND '3'"#
1831 /// );
1832 /// assert_eq!(
1833 /// query.to_string(PostgresQueryBuilder),
1834 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE 1 AND 2.5 AND '3'"#
1835 /// );
1836 /// assert_eq!(
1837 /// query.to_string(SqliteQueryBuilder),
1838 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE 1 AND 2.5 AND '3'"#
1839 /// );
1840 /// ```
1841 pub fn value<V>(v: V) -> Self
1842 where
1843 V: Into<Self>,
1844 {
1845 v.into()
1846 }
1847
1848 /// Express any custom expression in [`&str`].
1849 ///
1850 /// # Examples
1851 ///
1852 /// ```
1853 /// use sea_query::{tests_cfg::*, *};
1854 ///
1855 /// let query = Query::select()
1856 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
1857 /// .from(Char::Table)
1858 /// .and_where(Expr::cust("1 = 1"))
1859 /// .to_owned();
1860 ///
1861 /// assert_eq!(
1862 /// query.to_string(MysqlQueryBuilder),
1863 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE 1 = 1"#
1864 /// );
1865 /// assert_eq!(
1866 /// query.to_string(PostgresQueryBuilder),
1867 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE 1 = 1"#
1868 /// );
1869 /// assert_eq!(
1870 /// query.to_string(SqliteQueryBuilder),
1871 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE 1 = 1"#
1872 /// );
1873 /// ```
1874 pub fn cust<T>(s: T) -> Self
1875 where
1876 T: Into<String>,
1877 {
1878 Self::Custom(s.into())
1879 }
1880
1881 /// Express any custom expression with [`Value`]. Use this if your expression needs variables.
1882 ///
1883 /// # Examples
1884 ///
1885 /// ```
1886 /// use sea_query::{tests_cfg::*, *};
1887 ///
1888 /// let query = Query::select()
1889 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
1890 /// .from(Char::Table)
1891 /// .and_where(Expr::col(Char::Id).eq(1))
1892 /// .and_where(Expr::cust_with_values("6 = ? * ?", [2, 3]))
1893 /// .to_owned();
1894 ///
1895 /// assert_eq!(
1896 /// query.to_string(MysqlQueryBuilder),
1897 /// r#"SELECT `character`, `size_w`, `size_h` FROM `character` WHERE `id` = 1 AND (6 = 2 * 3)"#
1898 /// );
1899 /// assert_eq!(
1900 /// query.to_string(SqliteQueryBuilder),
1901 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "id" = 1 AND (6 = 2 * 3)"#
1902 /// );
1903 /// ```
1904 /// ```
1905 /// use sea_query::{tests_cfg::*, *};
1906 ///
1907 /// let query = Query::select()
1908 /// .columns([Char::Character, Char::SizeW, Char::SizeH])
1909 /// .from(Char::Table)
1910 /// .and_where(Expr::col(Char::Id).eq(1))
1911 /// .and_where(Expr::cust_with_values("6 = $2 * $1", [3, 2]))
1912 /// .to_owned();
1913 ///
1914 /// assert_eq!(
1915 /// query.to_string(PostgresQueryBuilder),
1916 /// r#"SELECT "character", "size_w", "size_h" FROM "character" WHERE "id" = 1 AND (6 = 2 * 3)"#
1917 /// );
1918 /// ```
1919 /// ```
1920 /// use sea_query::{tests_cfg::*, *};
1921 ///
1922 /// let query = Query::select()
1923 /// .expr(Expr::cust_with_values("6 = ? * ?", [2, 3]))
1924 /// .to_owned();
1925 ///
1926 /// assert_eq!(query.to_string(MysqlQueryBuilder), r#"SELECT 6 = 2 * 3"#);
1927 /// assert_eq!(query.to_string(SqliteQueryBuilder), r#"SELECT 6 = 2 * 3"#);
1928 /// ```
1929 /// Postgres only: use `$$` to escape `$`
1930 /// ```
1931 /// use sea_query::{tests_cfg::*, *};
1932 ///
1933 /// let query = Query::select()
1934 /// .expr(Expr::cust_with_values("$1 $$ $2", ["a", "b"]))
1935 /// .to_owned();
1936 ///
1937 /// assert_eq!(query.to_string(PostgresQueryBuilder), r#"SELECT 'a' $ 'b'"#);
1938 /// ```
1939 /// ```
1940 /// use sea_query::{tests_cfg::*, *};
1941 ///
1942 /// let query = Query::select()
1943 /// .expr(Expr::cust_with_values("data @? ($1::JSONPATH)", ["hello"]))
1944 /// .to_owned();
1945 ///
1946 /// assert_eq!(
1947 /// query.to_string(PostgresQueryBuilder),
1948 /// r#"SELECT data @? ('hello'::JSONPATH)"#
1949 /// );
1950 /// ```
1951 pub fn cust_with_values<T, V, I>(s: T, v: I) -> Self
1952 where
1953 T: Into<String>,
1954 V: Into<Value>,
1955 I: IntoIterator<Item = V>,
1956 {
1957 Self::CustomWithExpr(
1958 s.into(),
1959 v.into_iter()
1960 .map(|v| Into::<Value>::into(v).into())
1961 .collect(),
1962 )
1963 }
1964
1965 /// Express any custom expression with [`Expr`]. Use this if your expression needs other expression.
1966 ///
1967 /// # Examples
1968 ///
1969 /// ```
1970 /// use sea_query::{tests_cfg::*, *};
1971 ///
1972 /// let query = Query::select()
1973 /// .expr(Expr::val(1).add(2))
1974 /// .expr(Expr::cust_with_expr("data @? ($1::JSONPATH)", "hello"))
1975 /// .to_owned();
1976 /// let (sql, values) = query.build(PostgresQueryBuilder);
1977 ///
1978 /// assert_eq!(sql, r#"SELECT $1 + $2, data @? ($3::JSONPATH)"#);
1979 /// assert_eq!(
1980 /// values,
1981 /// Values(vec![1i32.into(), 2i32.into(), "hello".into()])
1982 /// );
1983 /// ```
1984 /// ```
1985 /// use sea_query::{tests_cfg::*, *};
1986 ///
1987 /// let query = Query::select()
1988 /// .expr(Expr::cust_with_expr(
1989 /// "json_agg(DISTINCT $1)",
1990 /// Expr::col(Char::Character),
1991 /// ))
1992 /// .to_owned();
1993 ///
1994 /// assert_eq!(
1995 /// query.to_string(PostgresQueryBuilder),
1996 /// r#"SELECT json_agg(DISTINCT "character")"#
1997 /// );
1998 /// ```
1999 pub fn cust_with_expr<T, E>(s: T, expr: E) -> Self
2000 where
2001 T: Into<String>,
2002 E: Into<Self>,
2003 {
2004 Self::CustomWithExpr(s.into(), vec![expr.into()])
2005 }
2006
2007 /// Express any custom expression with [`Expr`]. Use this if your expression needs other expressions.
2008 pub fn cust_with_exprs<T, I>(s: T, v: I) -> Self
2009 where
2010 T: Into<String>,
2011 I: IntoIterator<Item = Expr>,
2012 {
2013 Self::CustomWithExpr(s.into(), v.into_iter().collect())
2014 }
2015
2016 /// Express a `MAX` function.
2017 ///
2018 /// # Examples
2019 ///
2020 /// ```
2021 /// use sea_query::{tests_cfg::*, *};
2022 ///
2023 /// let query = Query::select()
2024 /// .expr(Expr::col((Char::Table, Char::SizeW)).max())
2025 /// .from(Char::Table)
2026 /// .to_owned();
2027 ///
2028 /// assert_eq!(
2029 /// query.to_string(MysqlQueryBuilder),
2030 /// r#"SELECT MAX(`character`.`size_w`) FROM `character`"#
2031 /// );
2032 /// assert_eq!(
2033 /// query.to_string(PostgresQueryBuilder),
2034 /// r#"SELECT MAX("character"."size_w") FROM "character""#
2035 /// );
2036 /// assert_eq!(
2037 /// query.to_string(SqliteQueryBuilder),
2038 /// r#"SELECT MAX("character"."size_w") FROM "character""#
2039 /// );
2040 /// ```
2041 pub fn max(self) -> Self {
2042 Func::max(self).into()
2043 }
2044
2045 /// Express a `MIN` function.
2046 ///
2047 /// # Examples
2048 ///
2049 /// ```
2050 /// use sea_query::{tests_cfg::*, *};
2051 ///
2052 /// let query = Query::select()
2053 /// .expr(Expr::col((Char::Table, Char::SizeW)).min())
2054 /// .from(Char::Table)
2055 /// .to_owned();
2056 ///
2057 /// assert_eq!(
2058 /// query.to_string(MysqlQueryBuilder),
2059 /// r#"SELECT MIN(`character`.`size_w`) FROM `character`"#
2060 /// );
2061 /// assert_eq!(
2062 /// query.to_string(PostgresQueryBuilder),
2063 /// r#"SELECT MIN("character"."size_w") FROM "character""#
2064 /// );
2065 /// assert_eq!(
2066 /// query.to_string(SqliteQueryBuilder),
2067 /// r#"SELECT MIN("character"."size_w") FROM "character""#
2068 /// );
2069 /// ```
2070 pub fn min(self) -> Self {
2071 Func::min(self).into()
2072 }
2073
2074 /// Express a `SUM` function.
2075 ///
2076 /// # Examples
2077 ///
2078 /// ```
2079 /// use sea_query::{tests_cfg::*, *};
2080 ///
2081 /// let query = Query::select()
2082 /// .expr(Expr::col((Char::Table, Char::SizeW)).sum())
2083 /// .from(Char::Table)
2084 /// .to_owned();
2085 ///
2086 /// assert_eq!(
2087 /// query.to_string(MysqlQueryBuilder),
2088 /// r#"SELECT SUM(`character`.`size_w`) FROM `character`"#
2089 /// );
2090 /// assert_eq!(
2091 /// query.to_string(PostgresQueryBuilder),
2092 /// r#"SELECT SUM("character"."size_w") FROM "character""#
2093 /// );
2094 /// assert_eq!(
2095 /// query.to_string(SqliteQueryBuilder),
2096 /// r#"SELECT SUM("character"."size_w") FROM "character""#
2097 /// );
2098 /// ```
2099 pub fn sum(self) -> Self {
2100 Func::sum(self).into()
2101 }
2102
2103 /// Express a `COUNT` function.
2104 ///
2105 /// # Examples
2106 ///
2107 /// ```
2108 /// use sea_query::{tests_cfg::*, *};
2109 ///
2110 /// let query = Query::select()
2111 /// .expr(Expr::col((Char::Table, Char::SizeW)).count())
2112 /// .from(Char::Table)
2113 /// .to_owned();
2114 ///
2115 /// assert_eq!(
2116 /// query.to_string(MysqlQueryBuilder),
2117 /// r#"SELECT COUNT(`character`.`size_w`) FROM `character`"#
2118 /// );
2119 /// assert_eq!(
2120 /// query.to_string(PostgresQueryBuilder),
2121 /// r#"SELECT COUNT("character"."size_w") FROM "character""#
2122 /// );
2123 /// assert_eq!(
2124 /// query.to_string(SqliteQueryBuilder),
2125 /// r#"SELECT COUNT("character"."size_w") FROM "character""#
2126 /// );
2127 /// ```
2128 pub fn count(self) -> Self {
2129 Func::count(self).into()
2130 }
2131
2132 /// Express a `COUNT` function with the DISTINCT modifier.
2133 ///
2134 /// # Examples
2135 ///
2136 /// ```
2137 /// use sea_query::{tests_cfg::*, *};
2138 ///
2139 /// let query = Query::select()
2140 /// .expr(Expr::col((Char::Table, Char::SizeW)).count_distinct())
2141 /// .from(Char::Table)
2142 /// .to_owned();
2143 ///
2144 /// assert_eq!(
2145 /// query.to_string(MysqlQueryBuilder),
2146 /// r#"SELECT COUNT(DISTINCT `character`.`size_w`) FROM `character`"#
2147 /// );
2148 /// assert_eq!(
2149 /// query.to_string(PostgresQueryBuilder),
2150 /// r#"SELECT COUNT(DISTINCT "character"."size_w") FROM "character""#
2151 /// );
2152 /// assert_eq!(
2153 /// query.to_string(SqliteQueryBuilder),
2154 /// r#"SELECT COUNT(DISTINCT "character"."size_w") FROM "character""#
2155 /// );
2156 /// ```
2157 pub fn count_distinct(self) -> Self {
2158 Func::count_distinct(self).into()
2159 }
2160
2161 /// Express a `IF NULL` function.
2162 ///
2163 /// # Examples
2164 ///
2165 /// ```
2166 /// use sea_query::{tests_cfg::*, *};
2167 ///
2168 /// let query = Query::select()
2169 /// .expr(Expr::col((Char::Table, Char::SizeW)).if_null(0))
2170 /// .from(Char::Table)
2171 /// .to_owned();
2172 ///
2173 /// assert_eq!(
2174 /// query.to_string(MysqlQueryBuilder),
2175 /// r#"SELECT IFNULL(`character`.`size_w`, 0) FROM `character`"#
2176 /// );
2177 /// assert_eq!(
2178 /// query.to_string(PostgresQueryBuilder),
2179 /// r#"SELECT COALESCE("character"."size_w", 0) FROM "character""#
2180 /// );
2181 /// assert_eq!(
2182 /// query.to_string(SqliteQueryBuilder),
2183 /// r#"SELECT IFNULL("character"."size_w", 0) FROM "character""#
2184 /// );
2185 /// ```
2186 pub fn if_null<V>(self, v: V) -> Self
2187 where
2188 V: Into<Self>,
2189 {
2190 Func::if_null(self, v).into()
2191 }
2192
2193 /// Express a `EXISTS` sub-query expression.
2194 ///
2195 /// # Examples
2196 ///
2197 /// ```
2198 /// use sea_query::{*, tests_cfg::*};
2199 ///
2200 /// let query = Query::select()
2201 /// .expr_as(Expr::exists(Query::select().column(Char::Id).from(Char::Table).take()), "character_exists")
2202 /// .expr_as(Expr::exists(Query::select().column(Glyph::Id).from(Glyph::Table).take()), "glyph_exists")
2203 /// .to_owned();
2204 ///
2205 /// assert_eq!(
2206 /// query.to_string(MysqlQueryBuilder),
2207 /// r#"SELECT EXISTS(SELECT `id` FROM `character`) AS `character_exists`, EXISTS(SELECT `id` FROM `glyph`) AS `glyph_exists`"#
2208 /// );
2209 /// assert_eq!(
2210 /// query.to_string(PostgresQueryBuilder),
2211 /// r#"SELECT EXISTS(SELECT "id" FROM "character") AS "character_exists", EXISTS(SELECT "id" FROM "glyph") AS "glyph_exists""#
2212 /// );
2213 /// assert_eq!(
2214 /// query.to_string(SqliteQueryBuilder),
2215 /// r#"SELECT EXISTS(SELECT "id" FROM "character") AS "character_exists", EXISTS(SELECT "id" FROM "glyph") AS "glyph_exists""#
2216 /// );
2217 /// ```
2218 pub fn exists(sel: SelectStatement) -> Self {
2219 Self::SubQuery(Some(SubQueryOper::Exists), Box::new(sel.into()))
2220 }
2221
2222 /// Express a `ANY` sub-query expression.
2223 ///
2224 /// # Examples
2225 ///
2226 /// ```
2227 /// use sea_query::{tests_cfg::*, *};
2228 ///
2229 /// let query = Query::select()
2230 /// .column(Char::Id)
2231 /// .from(Char::Table)
2232 /// .and_where(Expr::col(Char::Id).eq(Expr::any(
2233 /// Query::select().column(Char::Id).from(Char::Table).take(),
2234 /// )))
2235 /// .to_owned();
2236 ///
2237 /// assert_eq!(
2238 /// query.to_string(MysqlQueryBuilder),
2239 /// r#"SELECT `id` FROM `character` WHERE `id` = ANY(SELECT `id` FROM `character`)"#
2240 /// );
2241 /// assert_eq!(
2242 /// query.to_string(PostgresQueryBuilder),
2243 /// r#"SELECT "id" FROM "character" WHERE "id" = ANY(SELECT "id" FROM "character")"#
2244 /// );
2245 /// ```
2246 pub fn any(sel: SelectStatement) -> Self {
2247 Self::SubQuery(Some(SubQueryOper::Any), Box::new(sel.into()))
2248 }
2249
2250 /// Express a `SOME` sub-query expression.
2251 ///
2252 /// # Examples
2253 ///
2254 /// ```
2255 /// use sea_query::{tests_cfg::*, *};
2256 ///
2257 /// let query = Query::select()
2258 /// .column(Char::Id)
2259 /// .from(Char::Table)
2260 /// .and_where(Expr::col(Char::Id).ne(Expr::some(
2261 /// Query::select().column(Char::Id).from(Char::Table).take(),
2262 /// )))
2263 /// .to_owned();
2264 ///
2265 /// assert_eq!(
2266 /// query.to_string(MysqlQueryBuilder),
2267 /// r#"SELECT `id` FROM `character` WHERE `id` <> SOME(SELECT `id` FROM `character`)"#
2268 /// );
2269 /// assert_eq!(
2270 /// query.to_string(PostgresQueryBuilder),
2271 /// r#"SELECT "id" FROM "character" WHERE "id" <> SOME(SELECT "id" FROM "character")"#
2272 /// );
2273 /// ```
2274 pub fn some(sel: SelectStatement) -> Self {
2275 Self::SubQuery(Some(SubQueryOper::Some), Box::new(sel.into()))
2276 }
2277
2278 /// Express a `ALL` sub-query expression.
2279 pub fn all(sel: SelectStatement) -> Self {
2280 Self::SubQuery(Some(SubQueryOper::All), Box::new(sel.into()))
2281 }
2282
2283 /// Adds new `CASE WHEN` to existing case statement.
2284 ///
2285 /// # Examples
2286 ///
2287 /// ```
2288 /// use sea_query::{*, tests_cfg::*};
2289 ///
2290 /// let query = Query::select()
2291 /// .expr_as(
2292 /// Expr::case(
2293 /// Expr::col((Glyph::Table, Glyph::Aspect)).is_in([2, 4]),
2294 /// true
2295 /// )
2296 /// .finally(false),
2297 /// "is_even"
2298 /// )
2299 /// .from(Glyph::Table)
2300 /// .to_owned();
2301 ///
2302 /// assert_eq!(
2303 /// query.to_string(PostgresQueryBuilder),
2304 /// r#"SELECT (CASE WHEN ("glyph"."aspect" IN (2, 4)) THEN TRUE ELSE FALSE END) AS "is_even" FROM "glyph""#
2305 /// );
2306 /// ```
2307 pub fn case<C, T>(cond: C, then: T) -> CaseStatement
2308 where
2309 C: IntoCondition,
2310 T: Into<Self>,
2311 {
2312 CaseStatement::new().case(cond, then)
2313 }
2314
2315 /// Keyword `CURRENT_DATE`.
2316 ///
2317 /// # Examples
2318 ///
2319 /// ```
2320 /// use sea_query::*;
2321 ///
2322 /// let query = Query::select().expr(Expr::current_date()).to_owned();
2323 ///
2324 /// assert_eq!(query.to_string(MysqlQueryBuilder), r#"SELECT CURRENT_DATE"#);
2325 /// assert_eq!(
2326 /// query.to_string(PostgresQueryBuilder),
2327 /// r#"SELECT CURRENT_DATE"#
2328 /// );
2329 /// assert_eq!(
2330 /// query.to_string(SqliteQueryBuilder),
2331 /// r#"SELECT CURRENT_DATE"#
2332 /// );
2333 /// ```
2334 pub fn current_date() -> Self {
2335 Self::Keyword(Keyword::CurrentDate)
2336 }
2337
2338 /// Keyword `CURRENT_TIMESTAMP`.
2339 ///
2340 /// # Examples
2341 ///
2342 /// ```
2343 /// use sea_query::*;
2344 ///
2345 /// let query = Query::select().expr(Expr::current_time()).to_owned();
2346 ///
2347 /// assert_eq!(query.to_string(MysqlQueryBuilder), r#"SELECT CURRENT_TIME"#);
2348 /// assert_eq!(
2349 /// query.to_string(PostgresQueryBuilder),
2350 /// r#"SELECT CURRENT_TIME"#
2351 /// );
2352 /// assert_eq!(
2353 /// query.to_string(SqliteQueryBuilder),
2354 /// r#"SELECT CURRENT_TIME"#
2355 /// );
2356 /// ```
2357 pub fn current_time() -> Self {
2358 Self::Keyword(Keyword::CurrentTime)
2359 }
2360
2361 /// Keyword `CURRENT_TIMESTAMP`.
2362 ///
2363 /// # Examples
2364 ///
2365 /// ```
2366 /// use sea_query::{Expr, MysqlQueryBuilder, PostgresQueryBuilder, Query, SqliteQueryBuilder};
2367 ///
2368 /// let query = Query::select().expr(Expr::current_timestamp()).to_owned();
2369 ///
2370 /// assert_eq!(
2371 /// query.to_string(MysqlQueryBuilder),
2372 /// r#"SELECT CURRENT_TIMESTAMP"#
2373 /// );
2374 /// assert_eq!(
2375 /// query.to_string(PostgresQueryBuilder),
2376 /// r#"SELECT CURRENT_TIMESTAMP"#
2377 /// );
2378 /// assert_eq!(
2379 /// query.to_string(SqliteQueryBuilder),
2380 /// r#"SELECT CURRENT_TIMESTAMP"#
2381 /// );
2382 /// ```
2383 pub fn current_timestamp() -> Self {
2384 Self::Keyword(Keyword::CurrentTimestamp)
2385 }
2386
2387 /// Keyword `DEFAULT`.
2388 ///
2389 /// SQLite does not support VALUES (DEFAULT).
2390 ///
2391 /// # Examples
2392 ///
2393 /// ```
2394 /// use sea_query::{
2395 /// Expr, MysqlQueryBuilder, PostgresQueryBuilder, Query, SqliteQueryBuilder, tests_cfg::*,
2396 /// };
2397 ///
2398 /// let query = Query::insert()
2399 /// .columns([Char::Id])
2400 /// .values_panic([Expr::keyword_default()])
2401 /// .to_owned();
2402 ///
2403 /// assert_eq!(
2404 /// query.to_string(MysqlQueryBuilder),
2405 /// r#"INSERT (`id`) VALUES (DEFAULT)"#
2406 /// );
2407 /// assert_eq!(
2408 /// query.to_string(PostgresQueryBuilder),
2409 /// r#"INSERT ("id") VALUES (DEFAULT)"#
2410 /// );
2411 /// ```
2412 pub fn keyword_default() -> Self {
2413 Self::Keyword(Keyword::Default)
2414 }
2415
2416 /// Custom keyword.
2417 ///
2418 /// # Examples
2419 ///
2420 /// ```
2421 /// use sea_query::*;
2422 ///
2423 /// let query = Query::select()
2424 /// .expr(Expr::custom_keyword("test"))
2425 /// .to_owned();
2426 ///
2427 /// assert_eq!(query.to_string(MysqlQueryBuilder), r#"SELECT test"#);
2428 /// assert_eq!(query.to_string(PostgresQueryBuilder), r#"SELECT test"#);
2429 /// assert_eq!(query.to_string(SqliteQueryBuilder), r#"SELECT test"#);
2430 /// ```
2431 pub fn custom_keyword<T>(i: T) -> Self
2432 where
2433 T: IntoIden,
2434 {
2435 Self::Keyword(Keyword::Custom(i.into_iden()))
2436 }
2437}
2438
2439impl<T> From<T> for Expr
2440where
2441 T: Into<Value>,
2442{
2443 fn from(v: T) -> Self {
2444 Self::Value(v.into())
2445 }
2446}
2447
2448impl From<FunctionCall> for Expr {
2449 fn from(func: FunctionCall) -> Self {
2450 Self::FunctionCall(func)
2451 }
2452}
2453
2454impl From<ColumnRef> for Expr {
2455 fn from(col: ColumnRef) -> Self {
2456 Self::Column(col)
2457 }
2458}
2459
2460impl From<Keyword> for Expr {
2461 fn from(k: Keyword) -> Self {
2462 Self::Keyword(k)
2463 }
2464}
2465
2466impl From<LikeExpr> for Expr {
2467 fn from(like: LikeExpr) -> Self {
2468 match like.escape {
2469 Some(escape) => Self::Binary(
2470 Box::new(like.pattern.into()),
2471 BinOper::Escape,
2472 Box::new(Expr::Constant(escape.into())),
2473 ),
2474 None => like.pattern.into(),
2475 }
2476 }
2477}
2478
2479impl Expr {
2480 pub(crate) fn is_binary(&self) -> bool {
2481 matches!(self, Self::Binary(_, _, _))
2482 }
2483
2484 pub(crate) fn get_bin_oper(&self) -> Option<&BinOper> {
2485 match self {
2486 Self::Binary(_, oper, _) => Some(oper),
2487 _ => None,
2488 }
2489 }
2490}