rust_query/
lib.rs

1#![allow(private_bounds)]
2#![doc = include_str!("../README.md")]
3
4extern crate self as rust_query;
5
6mod aggregate;
7mod alias;
8mod ast;
9mod client;
10mod db;
11mod dummy;
12mod exec;
13mod hash;
14mod insert;
15mod migrate;
16mod mymap;
17mod pragma;
18mod ref_cast_impl;
19mod rows;
20mod token;
21mod transaction;
22mod value;
23
24pub use crate::dummy::Dummy;
25pub use aggregate::aggregate;
26pub use db::TableRow;
27use hash::TypBuilder;
28use ref_cast::RefCast;
29pub use rows::Rows;
30pub use rust_query_macros::FromDummy;
31pub use token::LocalClient;
32pub use transaction::{Database, Transaction, TransactionMut, TransactionWeak};
33pub use value::{Column, IntoColumn, UnixEpoch};
34
35/// Types that are used as closure arguments.
36///
37/// You generally don't need to import these types.
38pub mod args {
39    pub use crate::aggregate::Aggregate;
40    pub use crate::exec::Query;
41}
42
43/// Types to declare schemas and migrations.
44///
45/// A good starting point is too look at [crate::migration::schema].
46pub mod migration {
47    pub use crate::migrate::{Alter, Config, Create, Migrator, NoTable};
48    pub use expect_test::expect;
49    pub use rust_query_macros::schema;
50}
51
52/// These items are only exposed for use by the proc macros.
53/// Direct use is unsupported.
54#[doc(hidden)]
55pub mod private {
56    pub use crate::db::Col;
57    pub use crate::dummy::{Cached, Cacher, Dummy, Row};
58    pub use crate::exec::show_sql;
59    pub use crate::hash::TypBuilder;
60    pub use crate::hash::{hash_schema, KangarooHasher};
61    pub use crate::insert::{Reader, Writable};
62    pub use crate::migrate::{
63        Migration, Schema, SchemaBuilder, TableCreation, TableMigration, TableTypBuilder, C, M,
64    };
65    pub use crate::value::{MyTyp, Typed, ValueBuilder};
66
67    pub use expect_test::Expect;
68    pub use ref_cast::RefCast;
69    pub use sea_query::SimpleExpr;
70}
71
72/// This trait is implemented for all table types as generated by the [crate::migration::schema] macro.
73///
74/// **You can not implement this trait yourself!**
75pub trait Table: Sized + 'static {
76    /// The associated type [Table::Ext] is used as the deref target by several types that implement [IntoColumn].
77    /// This adds convenient methods to access related tables that have a foreign key constraint.
78    #[doc(hidden)]
79    type Ext<T>: RefCast<From = T>;
80
81    /// The schema that this table is a part of.
82    type Schema;
83
84    /// Please refer to [Rows::join].
85    fn join<'inner>(rows: &mut Rows<'inner, Self::Schema>) -> Column<'inner, Self::Schema, Self> {
86        rows.join()
87    }
88
89    /// The type returned by the [Table::dummy] method.
90    type Dummy<'t>;
91
92    /// Create a dummy that can be used for [TransactionMut::try_insert] and [TransactionMut::try_update] etc.
93    /// ```rust,ignore
94    /// txn.find_and_update(User {
95    ///     email: new_email,
96    ///     ..user.dummy()
97    /// })
98    /// .unwrap();
99    /// ```
100    /// Note that all fields of the dummy have type [Column], so if you want to change the value to something that is not
101    /// a [Column], then you need to do one of the following:
102    /// - Turn the value into a [Column] with [IntoColumn::into_column].
103    /// - Use `#![feature(type_changing_struct_update)]`.
104    fn dummy<'t>(val: impl IntoColumn<'t, Self::Schema, Typ = Self>) -> Self::Dummy<'t>;
105
106    /// The type of error when a delete fails due to a foreign key constraint.
107    type Referer;
108
109    #[doc(hidden)]
110    fn get_referer_unchecked() -> Self::Referer;
111
112    // used for the first join (useful for pragmas)
113    #[doc(hidden)]
114    fn name(&self) -> String {
115        Self::NAME.to_owned()
116    }
117    #[doc(hidden)]
118    fn typs(f: &mut TypBuilder<Self::Schema>);
119
120    #[doc(hidden)]
121    const ID: &'static str = "";
122    #[doc(hidden)]
123    const NAME: &'static str = "";
124}
125
126#[test]
127fn compile_tests() {
128    let t = trybuild::TestCases::new();
129    t.compile_fail("tests/compile/*.rs");
130    t.pass("examples/*.rs");
131}