sea_orm_macros/
lib.rs

1extern crate proc_macro;
2
3use proc_macro::TokenStream;
4
5use syn::{parse_macro_input, DeriveInput, Error};
6
7#[cfg(feature = "derive")]
8mod derives;
9
10#[cfg(feature = "strum")]
11mod strum;
12
13/// Create an Entity
14///
15/// ### Usage
16///
17/// ```
18/// use sea_orm::entity::prelude::*;
19///
20/// #[derive(Copy, Clone, Default, Debug, DeriveEntity)]
21/// pub struct Entity;
22///
23/// # impl EntityName for Entity {
24/// #     fn table_name(&self) -> &str {
25/// #         "cake"
26/// #     }
27/// # }
28/// #
29/// # #[derive(Clone, Debug, PartialEq, DeriveModel, DeriveActiveModel)]
30/// # pub struct Model {
31/// #     pub id: i32,
32/// #     pub name: String,
33/// # }
34/// #
35/// # #[derive(Copy, Clone, Debug, EnumIter, DeriveColumn)]
36/// # pub enum Column {
37/// #     Id,
38/// #     Name,
39/// # }
40/// #
41/// # #[derive(Copy, Clone, Debug, EnumIter, DerivePrimaryKey)]
42/// # pub enum PrimaryKey {
43/// #     Id,
44/// # }
45/// #
46/// # impl PrimaryKeyTrait for PrimaryKey {
47/// #     type ValueType = i32;
48/// #
49/// #     fn auto_increment() -> bool {
50/// #         true
51/// #     }
52/// # }
53/// #
54/// # #[derive(Copy, Clone, Debug, EnumIter)]
55/// # pub enum Relation {}
56/// #
57/// # impl ColumnTrait for Column {
58/// #     type EntityName = Entity;
59/// #
60/// #     fn def(&self) -> ColumnDef {
61/// #         match self {
62/// #             Self::Id => ColumnType::Integer.def(),
63/// #             Self::Name => ColumnType::String(StringLen::None).def(),
64/// #         }
65/// #     }
66/// # }
67/// #
68/// # impl RelationTrait for Relation {
69/// #     fn def(&self) -> RelationDef {
70/// #         panic!("No Relation");
71/// #     }
72/// # }
73/// #
74/// # impl ActiveModelBehavior for ActiveModel {}
75/// ```
76#[cfg(feature = "derive")]
77#[proc_macro_derive(DeriveEntity, attributes(sea_orm))]
78pub fn derive_entity(input: TokenStream) -> TokenStream {
79    let input = parse_macro_input!(input as DeriveInput);
80    derives::expand_derive_entity(input)
81        .unwrap_or_else(Error::into_compile_error)
82        .into()
83}
84
85/// This derive macro is the 'almighty' macro which automatically generates
86/// Entity, Column, and PrimaryKey from a given Model.
87///
88/// ### Usage
89///
90/// ```
91/// use sea_orm::entity::prelude::*;
92/// use serde::{Deserialize, Serialize};
93///
94/// #[derive(Clone, Debug, PartialEq, DeriveEntityModel, Deserialize, Serialize)]
95/// #[sea_orm(table_name = "posts")]
96/// pub struct Model {
97///     #[sea_orm(primary_key)]
98///     pub id: i32,
99///     pub title: String,
100///     #[sea_orm(column_type = "Text")]
101///     pub text: String,
102/// }
103///
104/// # #[derive(Copy, Clone, Debug, EnumIter)]
105/// # pub enum Relation {}
106/// #
107/// # impl RelationTrait for Relation {
108/// #     fn def(&self) -> RelationDef {
109/// #         panic!("No Relation");
110/// #     }
111/// # }
112/// #
113/// # impl ActiveModelBehavior for ActiveModel {}
114/// ```
115///
116/// Entity should always have a primary key.
117/// Or, it will result in a compile error.
118/// See <https://github.com/SeaQL/sea-orm/issues/485> for details.
119///
120/// ```compile_fail
121/// use sea_orm::entity::prelude::*;
122///
123/// #[derive(Clone, Debug, PartialEq, DeriveEntityModel)]
124/// #[sea_orm(table_name = "posts")]
125/// pub struct Model {
126///     pub title: String,
127///     #[sea_orm(column_type = "Text")]
128///     pub text: String,
129/// }
130///
131/// # #[derive(Copy, Clone, Debug, EnumIter, DeriveRelation)]
132/// # pub enum Relation {}
133/// #
134/// # impl ActiveModelBehavior for ActiveModel {}
135/// ```
136#[cfg(feature = "derive")]
137#[proc_macro_derive(DeriveEntityModel, attributes(sea_orm))]
138pub fn derive_entity_model(input: TokenStream) -> TokenStream {
139    let input_ts = input.clone();
140    let DeriveInput {
141        ident, data, attrs, ..
142    } = parse_macro_input!(input as DeriveInput);
143
144    if ident != "Model" {
145        panic!("Struct name must be Model");
146    }
147
148    let mut ts: TokenStream = derives::expand_derive_entity_model(data, attrs)
149        .unwrap_or_else(Error::into_compile_error)
150        .into();
151    ts.extend([
152        derive_model(input_ts.clone()),
153        derive_active_model(input_ts),
154    ]);
155    ts
156}
157
158/// The DerivePrimaryKey derive macro will implement [PrimaryKeyToColumn]
159/// for PrimaryKey which defines tedious mappings between primary keys and columns.
160/// The [EnumIter] is also derived, allowing iteration over all enum variants.
161///
162/// ### Usage
163///
164/// ```
165/// use sea_orm::entity::prelude::*;
166///
167/// #[derive(Copy, Clone, Debug, EnumIter, DerivePrimaryKey)]
168/// pub enum PrimaryKey {
169///     CakeId,
170///     FillingId,
171/// }
172///
173/// # #[derive(Copy, Clone, Default, Debug, DeriveEntity)]
174/// # pub struct Entity;
175/// #
176/// # impl EntityName for Entity {
177/// #     fn table_name(&self) -> &str {
178/// #         "cake"
179/// #     }
180/// # }
181/// #
182/// # #[derive(Clone, Debug, PartialEq, DeriveModel, DeriveActiveModel)]
183/// # pub struct Model {
184/// #     pub cake_id: i32,
185/// #     pub filling_id: i32,
186/// # }
187/// #
188/// # #[derive(Copy, Clone, Debug, EnumIter, DeriveColumn)]
189/// # pub enum Column {
190/// #     CakeId,
191/// #     FillingId,
192/// # }
193/// #
194/// # #[derive(Copy, Clone, Debug, EnumIter)]
195/// # pub enum Relation {}
196/// #
197/// # impl ColumnTrait for Column {
198/// #     type EntityName = Entity;
199/// #
200/// #     fn def(&self) -> ColumnDef {
201/// #         match self {
202/// #             Self::CakeId => ColumnType::Integer.def(),
203/// #             Self::FillingId => ColumnType::Integer.def(),
204/// #         }
205/// #     }
206/// # }
207/// #
208/// # impl PrimaryKeyTrait for PrimaryKey {
209/// #     type ValueType = (i32, i32);
210/// #
211/// #     fn auto_increment() -> bool {
212/// #         false
213/// #     }
214/// # }
215/// #
216/// # impl RelationTrait for Relation {
217/// #     fn def(&self) -> RelationDef {
218/// #         panic!("No Relation");
219/// #     }
220/// # }
221/// #
222/// # impl ActiveModelBehavior for ActiveModel {}
223/// ```
224#[cfg(feature = "derive")]
225#[proc_macro_derive(DerivePrimaryKey, attributes(sea_orm))]
226pub fn derive_primary_key(input: TokenStream) -> TokenStream {
227    let DeriveInput { ident, data, .. } = parse_macro_input!(input);
228
229    match derives::expand_derive_primary_key(ident, data) {
230        Ok(ts) => ts.into(),
231        Err(e) => e.to_compile_error().into(),
232    }
233}
234
235/// The DeriveColumn derive macro will implement [ColumnTrait] for Columns.
236/// It defines the identifier of each column by implementing Iden and IdenStatic.
237/// The EnumIter is also derived, allowing iteration over all enum variants.
238///
239/// ### Usage
240///
241/// ```
242/// use sea_orm::entity::prelude::*;
243///
244/// #[derive(Copy, Clone, Debug, EnumIter, DeriveColumn)]
245/// pub enum Column {
246///     CakeId,
247///     FillingId,
248/// }
249/// ```
250#[cfg(feature = "derive")]
251#[proc_macro_derive(DeriveColumn, attributes(sea_orm))]
252pub fn derive_column(input: TokenStream) -> TokenStream {
253    let DeriveInput { ident, data, .. } = parse_macro_input!(input);
254
255    match derives::expand_derive_column(&ident, &data) {
256        Ok(ts) => ts.into(),
257        Err(e) => e.to_compile_error().into(),
258    }
259}
260
261/// Derive a column if column names are not in snake-case
262///
263/// ### Usage
264///
265/// ```
266/// use sea_orm::entity::prelude::*;
267///
268/// #[derive(Copy, Clone, Debug, EnumIter, DeriveCustomColumn)]
269/// pub enum Column {
270///     Id,
271///     Name,
272///     VendorId,
273/// }
274///
275/// impl IdenStatic for Column {
276///     fn as_str(&self) -> &str {
277///         match self {
278///             Self::Id => "id",
279///             _ => self.default_as_str(),
280///         }
281///     }
282/// }
283/// ```
284#[cfg(feature = "derive")]
285#[proc_macro_derive(DeriveCustomColumn)]
286pub fn derive_custom_column(input: TokenStream) -> TokenStream {
287    let DeriveInput { ident, data, .. } = parse_macro_input!(input);
288
289    match derives::expand_derive_custom_column(&ident, &data) {
290        Ok(ts) => ts.into(),
291        Err(e) => e.to_compile_error().into(),
292    }
293}
294
295/// The DeriveModel derive macro will implement ModelTrait for Model,
296/// which provides setters and getters for all attributes in the mod
297/// It also implements FromQueryResult to convert a query result into the corresponding Model.
298///
299/// ### Usage
300///
301/// ```
302/// use sea_orm::entity::prelude::*;
303///
304/// #[derive(Clone, Debug, PartialEq, DeriveModel, DeriveActiveModel)]
305/// pub struct Model {
306///     pub id: i32,
307///     pub name: String,
308/// }
309///
310/// # #[derive(Copy, Clone, Default, Debug, DeriveEntity)]
311/// # pub struct Entity;
312/// #
313/// # impl EntityName for Entity {
314/// #     fn table_name(&self) -> &str {
315/// #         "cake"
316/// #     }
317/// # }
318/// #
319/// # #[derive(Copy, Clone, Debug, EnumIter, DeriveColumn)]
320/// # pub enum Column {
321/// #     Id,
322/// #     Name,
323/// # }
324/// #
325/// # #[derive(Copy, Clone, Debug, EnumIter, DerivePrimaryKey)]
326/// # pub enum PrimaryKey {
327/// #     Id,
328/// # }
329/// #
330/// # impl PrimaryKeyTrait for PrimaryKey {
331/// #     type ValueType = i32;
332/// #
333/// #     fn auto_increment() -> bool {
334/// #         true
335/// #     }
336/// # }
337/// #
338/// # #[derive(Copy, Clone, Debug, EnumIter)]
339/// # pub enum Relation {}
340/// #
341/// # impl ColumnTrait for Column {
342/// #     type EntityName = Entity;
343/// #
344/// #     fn def(&self) -> ColumnDef {
345/// #         match self {
346/// #             Self::Id => ColumnType::Integer.def(),
347/// #             Self::Name => ColumnType::String(StringLen::None).def(),
348/// #         }
349/// #     }
350/// # }
351/// #
352/// # impl RelationTrait for Relation {
353/// #     fn def(&self) -> RelationDef {
354/// #         panic!("No Relation");
355/// #     }
356/// # }
357/// #
358/// # impl ActiveModelBehavior for ActiveModel {}
359/// ```
360#[cfg(feature = "derive")]
361#[proc_macro_derive(DeriveModel, attributes(sea_orm))]
362pub fn derive_model(input: TokenStream) -> TokenStream {
363    let input = parse_macro_input!(input as DeriveInput);
364    derives::expand_derive_model(input)
365        .unwrap_or_else(Error::into_compile_error)
366        .into()
367}
368
369/// The DeriveActiveModel derive macro will implement ActiveModelTrait for ActiveModel
370/// which provides setters and getters for all active values in the active model.
371///
372/// ### Usage
373///
374/// ```
375/// use sea_orm::entity::prelude::*;
376///
377/// #[derive(Clone, Debug, PartialEq, DeriveModel, DeriveActiveModel)]
378/// pub struct Model {
379///     pub id: i32,
380///     pub name: String,
381/// }
382///
383/// # #[derive(Copy, Clone, Default, Debug, DeriveEntity)]
384/// # pub struct Entity;
385/// #
386/// # impl EntityName for Entity {
387/// #     fn table_name(&self) -> &str {
388/// #         "cake"
389/// #     }
390/// # }
391/// #
392/// # #[derive(Copy, Clone, Debug, EnumIter, DeriveColumn)]
393/// # pub enum Column {
394/// #     Id,
395/// #     Name,
396/// # }
397/// #
398/// # #[derive(Copy, Clone, Debug, EnumIter, DerivePrimaryKey)]
399/// # pub enum PrimaryKey {
400/// #     Id,
401/// # }
402/// #
403/// # impl PrimaryKeyTrait for PrimaryKey {
404/// #     type ValueType = i32;
405/// #
406/// #     fn auto_increment() -> bool {
407/// #         true
408/// #     }
409/// # }
410/// #
411/// # #[derive(Copy, Clone, Debug, EnumIter)]
412/// # pub enum Relation {}
413/// #
414/// # impl ColumnTrait for Column {
415/// #     type EntityName = Entity;
416/// #
417/// #     fn def(&self) -> ColumnDef {
418/// #         match self {
419/// #             Self::Id => ColumnType::Integer.def(),
420/// #             Self::Name => ColumnType::String(StringLen::None).def(),
421/// #         }
422/// #     }
423/// # }
424/// #
425/// # impl RelationTrait for Relation {
426/// #     fn def(&self) -> RelationDef {
427/// #         panic!("No Relation");
428/// #     }
429/// # }
430/// #
431/// # impl ActiveModelBehavior for ActiveModel {}
432/// ```
433#[cfg(feature = "derive")]
434#[proc_macro_derive(DeriveActiveModel, attributes(sea_orm))]
435pub fn derive_active_model(input: TokenStream) -> TokenStream {
436    let DeriveInput { ident, data, .. } = parse_macro_input!(input);
437
438    match derives::expand_derive_active_model(ident, data) {
439        Ok(ts) => ts.into(),
440        Err(e) => e.to_compile_error().into(),
441    }
442}
443
444/// Derive into an active model
445#[cfg(feature = "derive")]
446#[proc_macro_derive(DeriveIntoActiveModel, attributes(sea_orm))]
447pub fn derive_into_active_model(input: TokenStream) -> TokenStream {
448    let input = parse_macro_input!(input as DeriveInput);
449    derives::expand_into_active_model(input)
450        .unwrap_or_else(Error::into_compile_error)
451        .into()
452}
453
454/// Models that a user can override
455///
456/// ### Usage
457///
458/// ```
459/// use sea_orm::entity::prelude::*;
460///
461/// #[derive(
462///     Clone, Debug, PartialEq, DeriveModel, DeriveActiveModel, DeriveActiveModelBehavior,
463/// )]
464/// pub struct Model {
465///     pub id: i32,
466///     pub name: String,
467/// }
468///
469/// # #[derive(Copy, Clone, Default, Debug, DeriveEntity)]
470/// # pub struct Entity;
471/// #
472/// # impl EntityName for Entity {
473/// #     fn table_name(&self) -> &str {
474/// #         "cake"
475/// #     }
476/// # }
477/// #
478/// # #[derive(Copy, Clone, Debug, EnumIter, DeriveColumn)]
479/// # pub enum Column {
480/// #     Id,
481/// #     Name,
482/// # }
483/// #
484/// # #[derive(Copy, Clone, Debug, EnumIter, DerivePrimaryKey)]
485/// # pub enum PrimaryKey {
486/// #     Id,
487/// # }
488/// #
489/// # impl PrimaryKeyTrait for PrimaryKey {
490/// #     type ValueType = i32;
491/// #
492/// #     fn auto_increment() -> bool {
493/// #         true
494/// #     }
495/// # }
496/// #
497/// # #[derive(Copy, Clone, Debug, EnumIter)]
498/// # pub enum Relation {}
499/// #
500/// # impl ColumnTrait for Column {
501/// #     type EntityName = Entity;
502/// #
503/// #     fn def(&self) -> ColumnDef {
504/// #         match self {
505/// #             Self::Id => ColumnType::Integer.def(),
506/// #             Self::Name => ColumnType::String(StringLen::None).def(),
507/// #         }
508/// #     }
509/// # }
510/// #
511/// # impl RelationTrait for Relation {
512/// #     fn def(&self) -> RelationDef {
513/// #         panic!("No Relation");
514/// #     }
515/// # }
516/// ```
517#[cfg(feature = "derive")]
518#[proc_macro_derive(DeriveActiveModelBehavior)]
519pub fn derive_active_model_behavior(input: TokenStream) -> TokenStream {
520    let DeriveInput { ident, data, .. } = parse_macro_input!(input);
521
522    match derives::expand_derive_active_model_behavior(ident, data) {
523        Ok(ts) => ts.into(),
524        Err(e) => e.to_compile_error().into(),
525    }
526}
527
528/// A derive macro to implement `sea_orm::ActiveEnum` trait for enums.
529///
530/// # Limitations
531///
532/// This derive macros can only be used on enums.
533///
534/// # Macro Attributes
535///
536/// All macro attributes listed below have to be annotated in the form of `#[sea_orm(attr = value)]`.
537///
538/// - For enum
539///     - `rs_type`: Define `ActiveEnum::Value`
540///         - Possible values: `String`, `i8`, `i16`, `i32`, `i64`, `u8`, `u16`, `u32`, `u64`
541///         - Note that value has to be passed as string, i.e. `rs_type = "i8"`
542///     - `db_type`: Define `ColumnType` returned by `ActiveEnum::db_type()`
543///         - Possible values: all available enum variants of `ColumnType`, e.g. `String(StringLen::None)`, `String(StringLen::N(1))`, `Integer`
544///         - Note that value has to be passed as string, i.e. `db_type = "Integer"`
545///     - `enum_name`: Define `String` returned by `ActiveEnum::name()`
546///         - This attribute is optional with default value being the name of enum in camel-case
547///         - Note that value has to be passed as string, i.e. `enum_name = "MyEnum"`
548///
549/// - For enum variant
550///     - `string_value` or `num_value`:
551///         - For `string_value`, value should be passed as string, i.e. `string_value = "A"`
552///             - Due to the way internal Enums are automatically derived, the following restrictions apply:
553///                 - members cannot share identical `string_value`, case-insensitive.
554///                 - in principle, any future Titlecased Rust keywords are not valid `string_value`.
555///         - For `num_value`, value should be passed as integer, i.e. `num_value = 1` or `num_value = 1i32`
556///         - Note that only one of it can be specified, and all variants of an enum have to annotate with the same `*_value` macro attribute
557///
558/// # Usage
559///
560/// ```
561/// use sea_orm::{entity::prelude::*, DeriveActiveEnum};
562///
563/// #[derive(EnumIter, DeriveActiveEnum)]
564/// #[sea_orm(rs_type = "i32", db_type = "Integer")]
565/// pub enum Color {
566///     Black = 0,
567///     White = 1,
568/// }
569/// ```
570#[cfg(feature = "derive")]
571#[proc_macro_derive(DeriveActiveEnum, attributes(sea_orm))]
572pub fn derive_active_enum(input: TokenStream) -> TokenStream {
573    let input = parse_macro_input!(input as DeriveInput);
574    match derives::expand_derive_active_enum(input) {
575        Ok(ts) => ts.into(),
576        Err(e) => e.to_compile_error().into(),
577    }
578}
579
580/// Convert a query result into the corresponding Model.
581///
582/// ### Attributes
583///
584/// - `skip`: will not try to pull this field from the query result. And set it to the default value of the type.
585/// - `nested`: allows nesting models. can be any type that implements `FromQueryResult`
586/// - `from_alias`: get the value from this column alias
587///
588/// ### Usage
589///
590/// For more complete examples, please refer to https://github.com/SeaQL/sea-orm/blob/master/tests/from_query_result_tests.rs
591///
592/// ```
593/// use sea_orm::{entity::prelude::*, FromQueryResult};
594///
595/// #[derive(FromQueryResult)]
596/// struct Cake {
597///     id: i32,
598///     name: String,
599///     #[sea_orm(nested)]
600///     bakery: Option<CakeBakery>,
601///     #[sea_orm(skip)]
602///     skip_me: i32,
603/// }
604///
605/// #[derive(FromQueryResult)]
606/// struct CakeBakery {
607///     #[sea_orm(from_alias = "bakery_id")]
608///     id: i32,
609///     #[sea_orm(from_alias = "bakery_name")]
610///     title: String,
611/// }
612/// ```
613///
614/// You can compose this with regular Models, if there's no column collision:
615///
616/// ```ignore
617/// #[derive(FromQueryResult)]
618/// struct CakePlain {
619///     id: i32,
620///     name: String,
621///     price: Decimal,
622///     #[sea_orm(nested)]
623///     baker: Option<cakes_bakers::Model>,
624/// }
625/// ```
626#[cfg(feature = "derive")]
627#[proc_macro_derive(FromQueryResult, attributes(sea_orm))]
628pub fn derive_from_query_result(input: TokenStream) -> TokenStream {
629    let derive_input = parse_macro_input!(input);
630
631    match derives::expand_derive_from_query_result(derive_input) {
632        Ok(token_stream) => token_stream.into(),
633        Err(e) => e.to_compile_error().into(),
634    }
635}
636
637/// The DeriveRelation derive macro will implement RelationTrait for Relation.
638///
639/// ### Usage
640///
641/// ```
642/// # use sea_orm::tests_cfg::fruit::Entity;
643/// use sea_orm::entity::prelude::*;
644///
645/// #[derive(Copy, Clone, Debug, EnumIter, DeriveRelation)]
646/// pub enum Relation {
647///     #[sea_orm(
648///         belongs_to = "sea_orm::tests_cfg::cake::Entity",
649///         from = "sea_orm::tests_cfg::fruit::Column::CakeId",
650///         to = "sea_orm::tests_cfg::cake::Column::Id"
651///     )]
652///     Cake,
653///     #[sea_orm(
654///         belongs_to = "sea_orm::tests_cfg::cake_expanded::Entity",
655///         from = "sea_orm::tests_cfg::fruit::Column::CakeId",
656///         to = "sea_orm::tests_cfg::cake_expanded::Column::Id"
657///     )]
658///     CakeExpanded,
659/// }
660/// ```
661#[cfg(feature = "derive")]
662#[proc_macro_derive(DeriveRelation, attributes(sea_orm))]
663pub fn derive_relation(input: TokenStream) -> TokenStream {
664    let input = parse_macro_input!(input as DeriveInput);
665    derives::expand_derive_relation(input)
666        .unwrap_or_else(Error::into_compile_error)
667        .into()
668}
669
670/// The DeriveRelatedEntity derive macro will implement seaography::RelationBuilder for RelatedEntity enumeration.
671///
672/// ### Usage
673///
674/// ```ignore
675/// use sea_orm::entity::prelude::*;
676///
677/// // ...
678/// // Model, Relation enum, etc.
679/// // ...
680///
681/// #[derive(Copy, Clone, Debug, EnumIter, DeriveRelatedEntity)]
682/// pub enum RelatedEntity {
683///     #[sea_orm(entity = "super::address::Entity")]
684///     Address,
685///     #[sea_orm(entity = "super::payment::Entity")]
686///     Payment,
687///     #[sea_orm(entity = "super::rental::Entity")]
688///     Rental,
689///     #[sea_orm(entity = "Entity", def = "Relation::SelfRef.def()")]
690///     SelfRef,
691///     #[sea_orm(entity = "super::store::Entity")]
692///     Store,
693///     #[sea_orm(entity = "Entity", def = "Relation::SelfRef.def().rev()")]
694///     SelfRefRev,
695/// }
696/// ```
697#[cfg(feature = "derive")]
698#[proc_macro_derive(DeriveRelatedEntity, attributes(sea_orm))]
699pub fn derive_related_entity(input: TokenStream) -> TokenStream {
700    let input = parse_macro_input!(input as DeriveInput);
701    derives::expand_derive_related_entity(input)
702        .unwrap_or_else(Error::into_compile_error)
703        .into()
704}
705
706/// The DeriveMigrationName derive macro will implement `sea_orm_migration::MigrationName` for a migration.
707///
708/// ### Usage
709///
710/// ```ignore
711/// #[derive(DeriveMigrationName)]
712/// pub struct Migration;
713/// ```
714///
715/// The derive macro above will provide following implementation,
716/// given the file name is `m20220120_000001_create_post_table.rs`.
717///
718/// ```ignore
719/// impl MigrationName for Migration {
720///     fn name(&self) -> &str {
721///         "m20220120_000001_create_post_table"
722///     }
723/// }
724/// ```
725#[cfg(feature = "derive")]
726#[proc_macro_derive(DeriveMigrationName)]
727pub fn derive_migration_name(input: TokenStream) -> TokenStream {
728    let input = parse_macro_input!(input as DeriveInput);
729    derives::expand_derive_migration_name(input)
730        .unwrap_or_else(Error::into_compile_error)
731        .into()
732}
733
734#[cfg(feature = "derive")]
735#[proc_macro_derive(FromJsonQueryResult)]
736pub fn derive_from_json_query_result(input: TokenStream) -> TokenStream {
737    let DeriveInput { ident, .. } = parse_macro_input!(input);
738
739    match derives::expand_derive_from_json_query_result(ident) {
740        Ok(ts) => ts.into(),
741        Err(e) => e.to_compile_error().into(),
742    }
743}
744
745/// The DerivePartialModel derive macro will implement [`sea_orm::PartialModelTrait`] for simplify partial model queries.
746///
747/// ## Usage
748///
749/// For more complete examples, please refer to https://github.com/SeaQL/sea-orm/blob/master/tests/partial_model_tests.rs
750///
751/// ```rust
752/// use sea_orm::{entity::prelude::*, DerivePartialModel, FromQueryResult};
753///
754/// #[derive(Clone, Debug, PartialEq, DeriveEntityModel)]
755/// #[sea_orm(table_name = "posts")]
756/// pub struct Model {
757///     #[sea_orm(primary_key)]
758///     pub id: i32,
759///     pub title: String,
760///     #[sea_orm(column_type = "Text")]
761///     pub text: String,
762/// }
763/// # #[derive(Copy, Clone, Debug, DeriveRelation, EnumIter)]
764/// # pub enum Relation {}
765/// # impl ActiveModelBehavior for ActiveModel {}
766///
767/// #[derive(Debug, FromQueryResult, DerivePartialModel)]
768/// #[sea_orm(entity = "Entity")]
769/// struct SelectResult {
770///     title: String,
771///     #[sea_orm(from_col = "text")]
772///     content: String,
773///     #[sea_orm(from_expr = "Expr::val(1).add(1)")]
774///     sum: i32,
775/// }
776/// ```
777///
778/// If all fields in the partial model is `from_expr`, the specifying the `entity` can be skipped.
779/// ```
780/// use sea_orm::{entity::prelude::*, sea_query::Expr, DerivePartialModel, FromQueryResult};
781///
782/// #[derive(Debug, FromQueryResult, DerivePartialModel)]
783/// struct SelectResult {
784///     #[sea_orm(from_expr = "Expr::val(1).add(1)")]
785///     sum: i32,
786/// }
787/// ```
788///
789/// Since SeaORM 1.1.7, `DerivePartialModel` can also assumes the function of `FromQueryResult`.
790/// This is necessary to support nested partial models.
791///
792/// ```
793/// use sea_orm::{DerivePartialModel, FromQueryResult};
794/// #
795/// # mod cake {
796/// # use sea_orm::entity::prelude::*;
797/// # #[derive(Clone, Debug, DeriveEntityModel)]
798/// # #[sea_orm(table_name = "cake")]
799/// # pub struct Model {
800/// #     #[sea_orm(primary_key)]
801/// #     pub id: i32,
802/// #     pub name: String,
803/// # }
804/// # #[derive(Copy, Clone, Debug, DeriveRelation, EnumIter)]
805/// # pub enum Relation {}
806/// # impl ActiveModelBehavior for ActiveModel {}
807/// # }
808/// #
809/// # mod bakery {
810/// # use sea_orm::entity::prelude::*;
811/// # #[derive(Clone, Debug, DeriveEntityModel)]
812/// # #[sea_orm(table_name = "bakery")]
813/// # pub struct Model {
814/// #     #[sea_orm(primary_key)]
815/// #     pub id: i32,
816/// #     pub name: String,
817/// # }
818/// # #[derive(Copy, Clone, Debug, DeriveRelation, EnumIter)]
819/// # pub enum Relation {}
820/// # impl ActiveModelBehavior for ActiveModel {}
821/// # }
822///
823/// #[derive(DerivePartialModel)]
824/// #[sea_orm(entity = "cake::Entity", from_query_result)]
825/// struct Cake {
826///     id: i32,
827///     name: String,
828///     #[sea_orm(nested)]
829///     bakery: Option<Bakery>,
830///     #[sea_orm(skip)]
831///     ignore: String,
832/// }
833///
834/// #[derive(FromQueryResult, DerivePartialModel)]
835/// #[sea_orm(entity = "bakery::Entity")]
836/// struct Bakery {
837///     id: i32,
838///     #[sea_orm(from_col = "Name")]
839///     title: String,
840/// }
841///
842/// // In addition, there's an `alias` attribute to select the columns from an alias:
843///
844/// #[derive(DerivePartialModel)]
845/// #[sea_orm(entity = "bakery::Entity", alias = "factory", from_query_result)]
846/// struct Factory {
847///     id: i32,
848///     #[sea_orm(from_col = "name")]
849///     plant: String,
850/// }
851///
852/// #[derive(DerivePartialModel)]
853/// #[sea_orm(entity = "cake::Entity", from_query_result)]
854/// struct CakeFactory {
855///     id: i32,
856///     name: String,
857///     #[sea_orm(nested)]
858///     bakery: Option<Factory>,
859/// }
860/// ```
861///
862/// ```ignore
863/// let cake: CakeFactory = cake::Entity::find()
864///     .join_as(
865///         JoinType::LeftJoin,
866///         cake::Relation::Bakery.def(),
867///         "factory",
868///     )
869///     .order_by_asc(cake::Column::Id)
870///     .into_partial_model()
871///     .one(&db)
872///     .await
873///     .unwrap()
874///     .unwrap()
875///
876/// SELECT
877///     "cake"."id" AS "id", "cake"."name" AS "name",
878///     "factory"."id" AS "bakery_id", "factory"."name" AS "bakery_plant"
879/// FROM "cake"
880/// LEFT JOIN "bakery" AS "factory" ON "cake"."bakery_id" = "factory"."id"
881/// LIMIT 1
882/// ```
883///
884/// A field cannot have attributes `from_col`, `from_expr` or `nested` at the same time.
885/// Or, it will result in a compile error.
886///
887/// ```compile_fail
888/// use sea_orm::{entity::prelude::*, FromQueryResult, DerivePartialModel, sea_query::Expr};
889///
890/// #[derive(Debug, FromQueryResult, DerivePartialModel)]
891/// #[sea_orm(entity = "Entity")]
892/// struct SelectResult {
893///     #[sea_orm(from_expr = "Expr::val(1).add(1)", from_col = "foo")]
894///     sum: i32,
895/// }
896/// ```
897#[cfg(feature = "derive")]
898#[proc_macro_derive(DerivePartialModel, attributes(sea_orm))]
899pub fn derive_partial_model(input: TokenStream) -> TokenStream {
900    let derive_input = parse_macro_input!(input);
901
902    match derives::expand_derive_partial_model(derive_input) {
903        Ok(token_stream) => token_stream.into(),
904        Err(e) => e.to_compile_error().into(),
905    }
906}
907
908#[doc(hidden)]
909#[cfg(feature = "derive")]
910#[proc_macro_attribute]
911pub fn test(_: TokenStream, input: TokenStream) -> TokenStream {
912    let input = parse_macro_input!(input as syn::ItemFn);
913
914    let ret = &input.sig.output;
915    let name = &input.sig.ident;
916    let body = &input.block;
917    let attrs = &input.attrs;
918
919    quote::quote! (
920        #[test]
921        #[cfg(any(
922            feature = "sqlx-mysql",
923            feature = "sqlx-sqlite",
924            feature = "sqlx-postgres",
925        ))]
926        #(#attrs)*
927        fn #name() #ret {
928            let _ = ::tracing_subscriber::fmt()
929                .with_max_level(::tracing::Level::DEBUG)
930                .with_test_writer()
931                .try_init();
932            crate::block_on!(async { #body })
933        }
934    )
935    .into()
936}
937
938/// Creates a new type that iterates of the variants of an enum.
939///
940/// Iterate over the variants of an Enum. Any additional data on your variants will be set to `Default::default()`.
941/// The macro implements `strum::IntoEnumIterator` on your enum and creates a new type called `YourEnumIter` that is the iterator object.
942/// You cannot derive `EnumIter` on any type with a lifetime bound (`<'a>`) because the iterator would surely
943/// create [unbounded lifetimes](https://doc.rust-lang.org/nightly/nomicon/unbounded-lifetimes.html).
944#[cfg(feature = "strum")]
945#[proc_macro_derive(EnumIter, attributes(strum))]
946pub fn enum_iter(input: TokenStream) -> TokenStream {
947    let ast = parse_macro_input!(input as DeriveInput);
948
949    strum::enum_iter::enum_iter_inner(&ast)
950        .unwrap_or_else(Error::into_compile_error)
951        .into()
952}
953
954/// Implements traits for types that wrap a database value type.
955///
956/// This procedure macro implements `From<T> for Value`, `sea_orm::TryGetTable`, and
957/// `sea_query::ValueType` for the wrapper type `T`.
958///
959/// The wrapped type must be `sea_orm::Value` compatible.
960///
961/// ## Usage
962///
963/// ```rust
964/// use sea_orm::DeriveValueType;
965///
966/// #[derive(DeriveValueType)]
967/// struct MyString(String);
968///
969/// #[derive(DeriveValueType)]
970/// struct MyNumber(i32);
971/// ```
972///
973/// It's also possible to derive value type for enum-strings.
974/// Basically the underlying type is String, and the custom must implement methods `to_str` and `from_str`.
975///
976/// ## Example
977///
978/// ```rust
979/// use sea_orm::{sea_query::ValueTypeErr, DeriveValueType};
980///
981/// #[derive(DeriveValueType)]
982/// #[sea_orm(value_type = "String")]
983/// pub enum Tag {
984///     Hard,
985///     Soft,
986/// }
987///
988/// impl std::fmt::Display for Tag {
989///     fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
990///         write!(
991///             f,
992///             "{}",
993///             match self {
994///                 Self::Hard => "hard",
995///                 Self::Soft => "soft",
996///             }
997///         )
998///     }
999/// }
1000///
1001/// impl std::str::FromStr for Tag {
1002///     type Err = ValueTypeErr;
1003///
1004///     fn from_str(s: &str) -> Result<Self, Self::Err> {
1005///         Ok(match s {
1006///             "hard" => Self::Hard,
1007///             "soft" => Self::Soft,
1008///             _ => return Err(ValueTypeErr),
1009///         })
1010///     }
1011/// }
1012/// ```
1013///
1014/// `from_str` defaults to `std::str::FromStr::from_str`. `to_str` defaults to `std::string::ToString::to_string`.
1015/// They can be overridden with custom functions.
1016///
1017/// ```rust
1018/// use sea_orm::{sea_query::ValueTypeErr, DeriveValueType};
1019///
1020/// #[derive(DeriveValueType)]
1021/// #[sea_orm(
1022///     value_type = "String",
1023///     from_str = "Tag::from_str",
1024///     to_str = "Tag::to_str"
1025/// )]
1026/// pub enum Tag {
1027///     Color,
1028///     Grey,
1029/// }
1030///
1031/// impl Tag {
1032///     fn to_str(&self) -> &'static str {
1033///         match self {
1034///             Self::Color => "color",
1035///             Self::Grey => "grey",
1036///         }
1037///     }
1038///
1039///     fn from_str(s: &str) -> Result<Self, ValueTypeErr> {
1040///         Ok(match s {
1041///             "color" => Self::Color,
1042///             "grey" => Self::Grey,
1043///             _ => return Err(ValueTypeErr),
1044///         })
1045///     }
1046/// }
1047/// ```
1048#[cfg(feature = "derive")]
1049#[proc_macro_derive(DeriveValueType, attributes(sea_orm))]
1050pub fn derive_value_type(input: TokenStream) -> TokenStream {
1051    let derive_input = parse_macro_input!(input as DeriveInput);
1052    match derives::expand_derive_value_type(derive_input) {
1053        Ok(token_stream) => token_stream.into(),
1054        Err(e) => e.to_compile_error().into(),
1055    }
1056}
1057
1058#[cfg(feature = "derive")]
1059#[proc_macro_derive(DeriveDisplay, attributes(sea_orm))]
1060pub fn derive_active_enum_display(input: TokenStream) -> TokenStream {
1061    let input = parse_macro_input!(input as DeriveInput);
1062    match derives::expand_derive_active_enum_display(input) {
1063        Ok(ts) => ts.into(),
1064        Err(e) => e.to_compile_error().into(),
1065    }
1066}
1067
1068/// The DeriveIden derive macro will implement `sea_orm::sea_query::Iden` for simplify Iden implementation.
1069///
1070/// ## Usage
1071///
1072/// ```rust
1073/// use sea_orm::{DeriveIden, Iden};
1074///
1075/// #[derive(DeriveIden)]
1076/// pub enum MyClass {
1077///     Table, // this is a special case, which maps to the enum's name
1078///     Id,
1079///     #[sea_orm(iden = "turtle")]
1080///     Title,
1081///     Text,
1082/// }
1083///
1084/// #[derive(DeriveIden)]
1085/// struct MyOther;
1086///
1087/// assert_eq!(MyClass::Table.to_string(), "my_class");
1088/// assert_eq!(MyClass::Id.to_string(), "id");
1089/// assert_eq!(MyClass::Title.to_string(), "turtle"); // renamed!
1090/// assert_eq!(MyClass::Text.to_string(), "text");
1091/// assert_eq!(MyOther.to_string(), "my_other");
1092/// ```
1093#[cfg(feature = "derive")]
1094#[proc_macro_derive(DeriveIden, attributes(sea_orm))]
1095pub fn derive_iden(input: TokenStream) -> TokenStream {
1096    let derive_input = parse_macro_input!(input as DeriveInput);
1097
1098    match derives::expand_derive_iden(derive_input) {
1099        Ok(token_stream) => token_stream.into(),
1100        Err(e) => e.to_compile_error().into(),
1101    }
1102}