This commit is contained in:
2026-07-13 09:27:07 +02:00
parent 09cf5f37fb
commit 843dad8d79
18 changed files with 427 additions and 563 deletions
@@ -0,0 +1,106 @@
---
sessionId: session-260713-090509-126z
---
# Requirements
### Objectif
Migrer les entités SeaORM de `src/models` du format `Relation`/`DeriveRelation`/`Related` vers le format SeaORM 2.x basé sur `#[sea_orm::model]`, avec les relations `HasOne` et `HasMany`, sans modifier le schéma SQL ni les contrats applicatifs.
### Périmètre inclus
- Migrer les quatre modèles pilotes `attachment`, `category`, `channel` et `message`.
- Migrer ensuite les autres entités présentes sous `src/models` : `server`, `user`, `role`, `server_user`, `role_user`, `channel_user`, `channel_user_permission`, `channel_role_permission`, `server_user_permission`, `server_role_permission` et `computed_permission`.
- Préserver les noms de tables/colonnes, les types nullable, les clés primaires et les comportements `Cascade`, `SetNull` et `NoAction`.
- Conserver les implémentations `ActiveModelBehavior` et leurs valeurs par défaut (`Uuid::new_v4`/`Uuid::now_v7`, `is_default`, etc.).
- Utiliser la syntaxe effectivement supportée par `sea-orm 2.0.0-rc.42`.
### Hors périmètre
- Aucun changement dans `src/repositories`, `src/routes`, DTO, réponses HTTP ou frontend.
- Aucun changement dans `migration/src/m20220101_000001_create_table.rs` ou dans le schéma SQL.
- Aucun ajout de tests spécifiques demandé dans cette étape.
- Aucun mapping ORM artificiel pour `computed_permission.resource_id`, qui reste polymorphe entre serveur, catégorie et channel.
### Critères dacceptation
- Chaque entité migrée utilise un seul format SeaORM 2.x, sans ancien enum `Relation` ou `impl Related` résiduel inutile.
- Les relations pilotes compilent avec la release candidate déclarée.
- La relation auto-référente de `Message` expose un parent optionnel et plusieurs réponses, avec `SetNull` à la suppression du parent.
- Les champs relationnels ne deviennent pas des colonnes d`ActiveModel`.
- Les commandes de compilation intermédiaires et finales réussissent, sans exiger à ce stade ladaptation des repositories.
# Technical Design
### État actuel
- `Cargo.toml` déclare `sea-orm = 2.0.0-rc.42` avec les backends SQLite/Postgres/MySQL et `schema-sync`; le workspace utilise Rust édition 2024.
- Les fichiers `src/models/attachment.rs`, `category.rs`, `channel.rs` et `message.rs` utilisent actuellement `DeriveEntityModel`, un enum `Relation` avec `DeriveRelation`, puis des `impl Related<...>`.
- `message.rs` contient déjà les cas particuliers `reply_to_id: Option<Uuid>`, `ReplyTo` auto-référent avec `SetNull` et `Replies` via `via_rel`.
- `channel.rs` combine relations vers des champs nullable (`server_id`, `category_id`), une relation `HasMany` vers les messages et lenum SQL `ChannelType`.
- Les autres entités suivent le même patron généré; leurs relations existantes doivent être transposées sans élargir le périmètre fonctionnel.
- `src/repositories/server.rs` utilise `category::Entity::find().find_with_related(channel::Entity)`. Cet usage est explicitement laissé inchangé pour cette étape; la compatibilité de compilation sera constatée, et son adaptation fera lobjet dune étape ultérieure si nécessaire.
### Décisions
- **Migration incrémentale** : commencer par `attachment`, `category`, `channel`, `message`, lancer `cargo check`, puis migrer les entités restantes par groupes dépendants.
- **Relations dans `Model`** : représenter les relations parent/enfant avec les types SeaORM 2.x validés par la release candidate (`HasOne`/`HasMany` ou leur forme exacte requise), en conservant les cardinalités et actions SQL.
- **Schéma inchangé** : les attributs de relation refléteront les migrations existantes; aucune migration SQL ne sera ajoutée.
- **Polymorphisme explicite** : ne pas déclarer de relation sur `computed_permission.resource_id`.
- **ActiveModel séparé** : vérifier que les champs de relation sont ignorés par les insertions/mises à jour et que les constructeurs `new()` restent inchangés.
### Modifications proposées
- Dans chaque fichier `src/models/*.rs`, ajouter lattribut de modèle SeaORM 2.x et déplacer les relations du bloc `Relation` vers les champs relationnels de `Model`.
- Remplacer les `impl Related` et les enums `Relation` devenus inutiles, sans modifier les champs scalaires ni les dérivations nécessaires aux DTO/OpenAPI.
- Pour `message.rs`, représenter `channel`, `user`, `reply_to`, `attachments` et `replies`; préserver la relation inverse auto-référente et laction `on_delete = SetNull`.
- Pour `channel.rs`, conserver `Category`, `Server`, `Message` et `ChannelUser`, avec les relations optionnelles cohérentes avec `category_id` et `server_id`.
- Pour `server.rs`, `user.rs`, `role.rs` et les tables de jonction/permissions, transposer les relations présentes dans leurs enums actuels et vérifier les colonnes source/cible contre la migration.
- Ne pas modifier `src/models/mod.rs` ou `prelude.rs` sauf si la syntaxe SeaORM 2.x lexige pour résoudre les types dentités.
### Fichiers concernés
- Pilote : `src/models/attachment.rs`, `src/models/category.rs`, `src/models/channel.rs`, `src/models/message.rs`.
- Lots suivants : `src/models/server.rs`, `user.rs`, `role.rs`, `server_user.rs`, `role_user.rs`, `channel_user.rs`, `channel_user_permission.rs`, `channel_role_permission.rs`, `server_user_permission.rs`, `server_role_permission.rs`, `computed_permission.rs`.
- Référence en lecture seule : `migration/src/m20220101_000001_create_table.rs`.
- Explicitement non modifiés : `src/repositories/**`, `src/routes/**`, `frontend/**` et les migrations.
### Risques et garde-fous
- La syntaxe de `#[sea_orm::model]` et des relations auto-référentes peut différer entre la documentation stable et `rc.42`; valider la version verrouillée avant d’écrire les modèles.
- Les relations inverses et les relations multiples vers la même entité peuvent provoquer des ambiguïtés de nommage; utiliser des noms de champs distincts et compiler après chaque groupe.
- Une compilation peut révéler que `find_with_related` nécessite encore lancien trait `Related`; ne pas corriger les repositories dans cette étape, mais documenter précisément le blocage pour la suite.
- Comparer chaque relation avec la migration pour éviter de transformer une colonne polymorphe ou nullable en relation incorrecte.
# Testing
### Validation autorisée
La validation est volontairement limitée à la compilation, conformément au périmètre demandé.
- Après le groupe pilote, exécuter `cargo check`.
- Après chaque groupe dentités restant, exécuter `cargo check`.
- En fin de migration, exécuter `cargo fmt --all -- --check` puis `cargo check`.
- Vérifier par recherche statique que les entités migrées ne contiennent plus dancien enum `Relation` ou d`impl Related` inutile.
- Vérifier manuellement que les repositories et routes nont pas été modifiés; leurs adaptations et tests relationnels sont reportés.
# Delivery Steps
### ✓ Step 1: Migrer les quatre modèles pilotes
Les entités pilotes utilisent le format SeaORM 2.x et compilent avec la release candidate verrouillée.
- Adapter `src/models/attachment.rs`, `category.rs`, `channel.rs` et `message.rs`.
- Déclarer les relations dans `Model` avec les types et la syntaxe exacts supportés par `sea-orm 2.0.0-rc.42`.
- Préserver `ChannelType`, les champs optionnels et les actions `Cascade`, `SetNull` et `NoAction`.
- Représenter dans `message.rs` le parent `reply_to` et les `replies` sans relation sur une colonne polymorphe.
- Exécuter `cargo check` immédiatement après ce pilote.
### ✓ Step 2: Migrer les entités de base et de jonction
Les modèles de serveurs, utilisateurs, rôles et tables de jonction sont convertis sans changement de colonnes SQL.
- Migrer `server.rs`, `user.rs`, `role.rs`, `server_user.rs`, `role_user.rs` et `channel_user.rs`.
- Migrer les entités de permissions `channel_user_permission.rs`, `channel_role_permission.rs`, `server_user_permission.rs` et `server_role_permission.rs`.
- Transposer chaque relation existante avec ses colonnes source/cible et sa cardinalité.
- Conserver les implémentations `ActiveModelBehavior` et les valeurs par défaut propres à chaque modèle.
- Exécuter `cargo check` après ce groupe.
### ✓ Step 3: Finaliser le modèle polymorphe et nettoyer les anciens patrons
Toutes les entités de `src/models` utilisent exclusivement le format SeaORM 2.x, tandis que `computed_permission` conserve son champ polymorphe sans faux lien ORM.
- Migrer `src/models/computed_permission.rs` en conservant `resource_id` comme simple colonne.
- Supprimer dans les entités migrées les enums `Relation`, dérivations et `impl Related` devenus inutiles.
- Vérifier que les relations ne sont pas incluses dans les colonnes d`ActiveModel`.
- Contrôler les noms de champs relationnels et les éventuelles ambiguïtés de relations multiples.
- Exécuter `cargo fmt --all -- --check` puis `cargo check`.
- Ne modifier ni repositories, ni routes, ni migrations; relever séparément toute incompatibilité de `find_with_related` pour une future étape.
Generated
+2 -2
View File
@@ -4215,9 +4215,9 @@ dependencies = [
[[package]] [[package]]
name = "uuid" name = "uuid"
version = "1.23.4" version = "1.23.5"
source = "registry+https://github.com/rust-lang/crates.io-index" source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "bf80a72845275afea99e7f2b434723d3bc7e38470fcd1c7ed39a599c73319a53" checksum = "ea5fab0d6c3c01ae70085a09cb03d4c7a1d6314e2b3e075392783396d724ca0a"
dependencies = [ dependencies = [
"getrandom 0.4.3", "getrandom 0.4.3",
"js-sys", "js-sys",
+1 -1
View File
@@ -22,7 +22,7 @@ parking_lot = "0.12.5"
serde = "1.0.228" serde = "1.0.228"
serde_json = "1.0.150" serde_json = "1.0.150"
toml = "1.1.2" toml = "1.1.2"
uuid = { version = "1.23.4", features = ["v4", "v7", "fast-rng", "serde"] } uuid = { version = "1.23.5", features = ["v4", "v7", "fast-rng", "serde"] }
tracing = "0.1.44" tracing = "0.1.44"
tracing-subscriber = { version = "0.3", features = ["env-filter", "fmt", "time"] } tracing-subscriber = { version = "0.3", features = ["env-filter", "fmt", "time"] }
thiserror = "2" thiserror = "2"
+5 -14
View File
@@ -4,6 +4,7 @@ use sea_orm::entity::prelude::*;
use sea_orm::prelude::async_trait::async_trait; use sea_orm::prelude::async_trait::async_trait;
use sea_orm::Set; use sea_orm::Set;
#[sea_orm::model]
#[derive(Clone, Debug, PartialEq, DeriveEntityModel, Eq)] #[derive(Clone, Debug, PartialEq, DeriveEntityModel, Eq)]
#[sea_orm(table_name = "attachment")] #[sea_orm(table_name = "attachment")]
pub struct Model { pub struct Model {
@@ -14,24 +15,14 @@ pub struct Model {
pub file_size: i32, pub file_size: i32,
pub mime_type: String, pub mime_type: String,
pub created_at: DateTimeUtc, pub created_at: DateTimeUtc,
}
#[derive(Copy, Clone, Debug, EnumIter, DeriveRelation)]
pub enum Relation {
#[sea_orm( #[sea_orm(
belongs_to = "super::message::Entity", belongs_to,
from = "Column::MessageId", from = "message_id",
to = "super::message::Column::Id", to = "id",
on_update = "NoAction", on_update = "NoAction",
on_delete = "Cascade" on_delete = "Cascade"
)] )]
Message, pub message: HasOne<super::message::Entity>,
}
impl Related<super::message::Entity> for Entity {
fn to() -> RelationDef {
Relation::Message.def()
}
} }
#[async_trait] #[async_trait]
+7 -22
View File
@@ -4,6 +4,7 @@ use sea_orm::entity::prelude::*;
use sea_orm::prelude::async_trait::async_trait; use sea_orm::prelude::async_trait::async_trait;
use sea_orm::Set; use sea_orm::Set;
#[sea_orm::model]
#[derive(Clone, Debug, PartialEq, DeriveEntityModel, Eq)] #[derive(Clone, Debug, PartialEq, DeriveEntityModel, Eq)]
#[sea_orm(table_name = "category")] #[sea_orm(table_name = "category")]
pub struct Model { pub struct Model {
@@ -14,32 +15,16 @@ pub struct Model {
pub position: i32, pub position: i32,
pub created_at: DateTimeUtc, pub created_at: DateTimeUtc,
pub updated_at: DateTimeUtc, pub updated_at: DateTimeUtc,
} #[sea_orm(has_many)]
pub channels: HasMany<super::channel::Entity>,
#[derive(Copy, Clone, Debug, EnumIter, DeriveRelation)]
pub enum Relation {
#[sea_orm(has_many = "super::channel::Entity")]
Channel,
#[sea_orm( #[sea_orm(
belongs_to = "super::server::Entity", belongs_to,
from = "Column::ServerId", from = "server_id",
to = "super::server::Column::Id", to = "id",
on_update = "Cascade", on_update = "Cascade",
on_delete = "Cascade" on_delete = "Cascade"
)] )]
Server, pub server: HasOne<super::server::Entity>,
}
impl Related<super::channel::Entity> for Entity {
fn to() -> RelationDef {
Relation::Channel.def()
}
}
impl Related<super::server::Entity> for Entity {
fn to() -> RelationDef {
Relation::Server.def()
}
} }
#[async_trait] #[async_trait]
+13 -40
View File
@@ -20,6 +20,7 @@ pub enum ChannelType {
DM, DM,
} }
#[sea_orm::model]
#[derive(Clone, Debug, PartialEq, DeriveEntityModel, Eq)] #[derive(Clone, Debug, PartialEq, DeriveEntityModel, Eq)]
#[sea_orm(table_name = "channel")] #[sea_orm(table_name = "channel")]
pub struct Model { pub struct Model {
@@ -32,54 +33,26 @@ pub struct Model {
pub name: Option<String>, pub name: Option<String>,
pub created_at: DateTimeUtc, pub created_at: DateTimeUtc,
pub updated_at: DateTimeUtc, pub updated_at: DateTimeUtc,
}
#[derive(Copy, Clone, Debug, EnumIter, DeriveRelation)]
pub enum Relation {
#[sea_orm( #[sea_orm(
belongs_to = "super::category::Entity", belongs_to,
from = "Column::CategoryId", from = "category_id",
to = "super::category::Column::Id", to = "id",
on_update = "NoAction", on_update = "NoAction",
on_delete = "SetNull" on_delete = "SetNull"
)] )]
Category, pub category: HasOne<super::category::Entity>,
#[sea_orm(has_many = "super::channel_user::Entity")] #[sea_orm(has_many)]
ChannelUser, pub channel_users: HasMany<super::channel_user::Entity>,
#[sea_orm(has_many = "super::message::Entity")] #[sea_orm(has_many)]
Message, pub messages: HasMany<super::message::Entity>,
#[sea_orm( #[sea_orm(
belongs_to = "super::server::Entity", belongs_to,
from = "Column::ServerId", from = "server_id",
to = "super::server::Column::Id", to = "id",
on_update = "NoAction", on_update = "NoAction",
on_delete = "Cascade" on_delete = "Cascade"
)] )]
Server, pub server: HasOne<super::server::Entity>,
}
impl Related<super::category::Entity> for Entity {
fn to() -> RelationDef {
Relation::Category.def()
}
}
impl Related<super::channel_user::Entity> for Entity {
fn to() -> RelationDef {
Relation::ChannelUser.def()
}
}
impl Related<super::message::Entity> for Entity {
fn to() -> RelationDef {
Relation::Message.def()
}
}
impl Related<super::server::Entity> for Entity {
fn to() -> RelationDef {
Relation::Server.def()
}
} }
#[async_trait] #[async_trait]
+9 -25
View File
@@ -5,6 +5,7 @@ use sea_orm::entity::prelude::*;
use sea_orm::prelude::async_trait::async_trait; use sea_orm::prelude::async_trait::async_trait;
use sea_orm::{NotSet, Set}; use sea_orm::{NotSet, Set};
#[sea_orm::model]
#[derive(Clone, Debug, PartialEq, DeriveEntityModel, Eq)] #[derive(Clone, Debug, PartialEq, DeriveEntityModel, Eq)]
#[sea_orm(table_name = "channel_role_permission")] #[sea_orm(table_name = "channel_role_permission")]
pub struct Model { pub struct Model {
@@ -17,39 +18,22 @@ pub struct Model {
/// Bitmask des permissions accordées au rôle dans ce canal. /// Bitmask des permissions accordées au rôle dans ce canal.
pub permission: i64, pub permission: i64,
}
#[derive(Copy, Clone, Debug, EnumIter, DeriveRelation)]
pub enum Relation {
#[sea_orm( #[sea_orm(
belongs_to = "super::channel::Entity", belongs_to,
from = "Column::ChannelId", from = "channel_id",
to = "super::channel::Column::Id", to = "id",
on_update = "NoAction", on_update = "NoAction",
on_delete = "Cascade" on_delete = "Cascade"
)] )]
Channel, pub channel: HasOne<super::channel::Entity>,
#[sea_orm( #[sea_orm(
belongs_to = "super::role::Entity", belongs_to,
from = "Column::RoleId", from = "role_id",
to = "super::role::Column::Id", to = "id",
on_update = "NoAction", on_update = "NoAction",
on_delete = "Cascade" on_delete = "Cascade"
)] )]
Role, pub role: HasOne<super::role::Entity>,
}
impl Related<super::channel::Entity> for Entity {
fn to() -> RelationDef {
Relation::Channel.def()
}
}
impl Related<super::role::Entity> for Entity {
fn to() -> RelationDef {
Relation::Role.def()
}
} }
#[async_trait] #[async_trait]
+9 -24
View File
@@ -4,6 +4,7 @@ use sea_orm::entity::prelude::*;
use sea_orm::prelude::async_trait::async_trait; use sea_orm::prelude::async_trait::async_trait;
use sea_orm::Set; use sea_orm::Set;
#[sea_orm::model]
#[derive(Clone, Debug, PartialEq, DeriveEntityModel, Eq)] #[derive(Clone, Debug, PartialEq, DeriveEntityModel, Eq)]
#[sea_orm(table_name = "channel_user")] #[sea_orm(table_name = "channel_user")]
pub struct Model { pub struct Model {
@@ -13,38 +14,22 @@ pub struct Model {
pub user_id: Uuid, pub user_id: Uuid,
pub role: String, pub role: String,
pub joined_at: DateTimeUtc, pub joined_at: DateTimeUtc,
}
#[derive(Copy, Clone, Debug, EnumIter, DeriveRelation)]
pub enum Relation {
#[sea_orm( #[sea_orm(
belongs_to = "super::channel::Entity", belongs_to,
from = "Column::ChannelId", from = "channel_id",
to = "super::channel::Column::Id", to = "id",
on_update = "NoAction", on_update = "NoAction",
on_delete = "Cascade" on_delete = "Cascade"
)] )]
Channel, pub channel: HasOne<super::channel::Entity>,
#[sea_orm( #[sea_orm(
belongs_to = "super::user::Entity", belongs_to,
from = "Column::UserId", from = "user_id",
to = "super::user::Column::Id", to = "id",
on_update = "NoAction", on_update = "NoAction",
on_delete = "Cascade" on_delete = "Cascade"
)] )]
User, pub user: HasOne<super::user::Entity>,
}
impl Related<super::channel::Entity> for Entity {
fn to() -> RelationDef {
Relation::Channel.def()
}
}
impl Related<super::user::Entity> for Entity {
fn to() -> RelationDef {
Relation::User.def()
}
} }
#[async_trait] #[async_trait]
+9 -25
View File
@@ -5,6 +5,7 @@ use sea_orm::entity::prelude::*;
use sea_orm::prelude::async_trait::async_trait; use sea_orm::prelude::async_trait::async_trait;
use sea_orm::{NotSet, Set}; use sea_orm::{NotSet, Set};
#[sea_orm::model]
#[derive(Clone, Debug, PartialEq, DeriveEntityModel, Eq)] #[derive(Clone, Debug, PartialEq, DeriveEntityModel, Eq)]
#[sea_orm(table_name = "channel_user_permission")] #[sea_orm(table_name = "channel_user_permission")]
pub struct Model { pub struct Model {
@@ -17,39 +18,22 @@ pub struct Model {
/// Bitmask des permissions accordées directement à l'utilisateur dans ce canal. /// Bitmask des permissions accordées directement à l'utilisateur dans ce canal.
pub permission: i64, pub permission: i64,
}
#[derive(Copy, Clone, Debug, EnumIter, DeriveRelation)]
pub enum Relation {
#[sea_orm( #[sea_orm(
belongs_to = "super::channel::Entity", belongs_to,
from = "Column::ChannelId", from = "channel_id",
to = "super::channel::Column::Id", to = "id",
on_update = "NoAction", on_update = "NoAction",
on_delete = "Cascade" on_delete = "Cascade"
)] )]
Channel, pub channel: HasOne<super::channel::Entity>,
#[sea_orm( #[sea_orm(
belongs_to = "super::user::Entity", belongs_to,
from = "Column::UserId", from = "user_id",
to = "super::user::Column::Id", to = "id",
on_update = "NoAction", on_update = "NoAction",
on_delete = "Cascade" on_delete = "Cascade"
)] )]
User, pub user: HasOne<super::user::Entity>,
}
impl Related<super::channel::Entity> for Entity {
fn to() -> RelationDef {
Relation::Channel.def()
}
}
impl Related<super::user::Entity> for Entity {
fn to() -> RelationDef {
Relation::User.def()
}
} }
#[async_trait] #[async_trait]
+5 -14
View File
@@ -20,6 +20,7 @@ pub enum PermissionScopeType {
Channel, Channel,
} }
#[sea_orm::model]
#[derive(Clone, Debug, PartialEq, DeriveEntityModel, Eq)] #[derive(Clone, Debug, PartialEq, DeriveEntityModel, Eq)]
#[sea_orm(table_name = "computed_permission")] #[sea_orm(table_name = "computed_permission")]
pub struct Model { pub struct Model {
@@ -39,24 +40,14 @@ pub struct Model {
/// Cache des permissions serveur (stocké en i64 pour SQL, utilisé en u64) /// Cache des permissions serveur (stocké en i64 pour SQL, utilisé en u64)
pub server_permissions: i64, pub server_permissions: i64,
pub channel_permissions: i64, pub channel_permissions: i64,
}
#[derive(Copy, Clone, Debug, EnumIter, DeriveRelation)]
pub enum Relation {
#[sea_orm( #[sea_orm(
belongs_to = "super::user::Entity", belongs_to,
from = "Column::UserId", from = "user_id",
to = "super::user::Column::Id", to = "id",
on_update = "NoAction", on_update = "NoAction",
on_delete = "Cascade" on_delete = "Cascade"
)] )]
User, pub user: HasOne<super::user::Entity>,
}
impl Related<super::user::Entity> for Entity {
fn to() -> RelationDef {
Relation::User.def()
}
} }
#[async_trait] #[async_trait]
+19 -36
View File
@@ -4,6 +4,7 @@ use sea_orm::entity::prelude::*;
use sea_orm::prelude::async_trait::async_trait; use sea_orm::prelude::async_trait::async_trait;
use sea_orm::Set; use sea_orm::Set;
#[sea_orm::model]
#[derive(Clone, Debug, PartialEq, DeriveEntityModel, Eq)] #[derive(Clone, Debug, PartialEq, DeriveEntityModel, Eq)]
#[sea_orm(table_name = "message")] #[sea_orm(table_name = "message")]
pub struct Model { pub struct Model {
@@ -16,54 +17,36 @@ pub struct Model {
pub created_at: DateTimeUtc, pub created_at: DateTimeUtc,
pub updated_at: Option<DateTimeUtc>, pub updated_at: Option<DateTimeUtc>,
pub reply_to_id: Option<Uuid>, pub reply_to_id: Option<Uuid>,
} #[sea_orm(has_many)]
pub attachments: HasMany<super::attachment::Entity>,
#[derive(Copy, Clone, Debug, EnumIter, DeriveRelation)]
pub enum Relation {
#[sea_orm(has_many = "super::attachment::Entity")]
Attachment,
#[sea_orm( #[sea_orm(
belongs_to = "super::channel::Entity", belongs_to,
from = "Column::ChannelId", from = "channel_id",
to = "super::channel::Column::Id", to = "id",
on_update = "NoAction", on_update = "NoAction",
on_delete = "Cascade" on_delete = "Cascade"
)] )]
Channel, pub channel: HasOne<super::channel::Entity>,
#[sea_orm( #[sea_orm(
belongs_to = "Entity", self_ref,
from = "Column::ReplyToId", relation_enum = "ReplyTo",
to = "Column::Id", relation_reverse = "Replies",
from = "reply_to_id",
to = "id",
on_update = "NoAction", on_update = "NoAction",
on_delete = "SetNull" on_delete = "SetNull"
)] )]
SelfRef, pub reply_to: HasOne<Entity>,
#[sea_orm(self_ref, relation_enum = "Replies", relation_reverse = "ReplyTo")]
pub replies: HasMany<Entity>,
#[sea_orm( #[sea_orm(
belongs_to = "super::user::Entity", belongs_to,
from = "Column::UserId", from = "user_id",
to = "super::user::Column::Id", to = "id",
on_update = "NoAction", on_update = "NoAction",
on_delete = "Cascade" on_delete = "Cascade"
)] )]
User, pub user: HasOne<super::user::Entity>,
}
impl Related<super::attachment::Entity> for Entity {
fn to() -> RelationDef {
Relation::Attachment.def()
}
}
impl Related<super::channel::Entity> for Entity {
fn to() -> RelationDef {
Relation::Channel.def()
}
}
impl Related<super::user::Entity> for Entity {
fn to() -> RelationDef {
Relation::User.def()
}
} }
#[async_trait] #[async_trait]
+7 -22
View File
@@ -4,6 +4,7 @@ use sea_orm::entity::prelude::*;
use sea_orm::prelude::async_trait::async_trait; use sea_orm::prelude::async_trait::async_trait;
use sea_orm::Set; use sea_orm::Set;
#[sea_orm::model]
#[derive(Clone, Debug, PartialEq, DeriveEntityModel, Eq)] #[derive(Clone, Debug, PartialEq, DeriveEntityModel, Eq)]
#[sea_orm(table_name = "role")] #[sea_orm(table_name = "role")]
pub struct Model { pub struct Model {
@@ -13,32 +14,16 @@ pub struct Model {
pub name: String, pub name: String,
pub is_default: bool, pub is_default: bool,
pub created_at: DateTimeUtc, pub created_at: DateTimeUtc,
}
#[derive(Copy, Clone, Debug, EnumIter, DeriveRelation)]
pub enum Relation {
#[sea_orm( #[sea_orm(
belongs_to = "super::server::Entity", belongs_to,
from = "Column::ServerId", from = "server_id",
to = "super::server::Column::Id", to = "id",
on_update = "NoAction", on_update = "NoAction",
on_delete = "Cascade" on_delete = "Cascade"
)] )]
Server, pub server: HasOne<super::server::Entity>,
#[sea_orm(has_many = "super::role_user::Entity")] #[sea_orm(has_many)]
RoleUser, pub role_users: HasMany<super::role_user::Entity>,
}
impl Related<super::server::Entity> for Entity {
fn to() -> RelationDef {
Relation::Server.def()
}
}
impl Related<super::role_user::Entity> for Entity {
fn to() -> RelationDef {
Relation::RoleUser.def()
}
} }
#[async_trait] #[async_trait]
+9 -24
View File
@@ -2,6 +2,7 @@
use sea_orm::entity::prelude::*; use sea_orm::entity::prelude::*;
#[sea_orm::model]
#[derive(Clone, Debug, PartialEq, DeriveEntityModel, Eq)] #[derive(Clone, Debug, PartialEq, DeriveEntityModel, Eq)]
#[sea_orm(table_name = "role_user")] #[sea_orm(table_name = "role_user")]
pub struct Model { pub struct Model {
@@ -9,38 +10,22 @@ pub struct Model {
pub role_id: Uuid, pub role_id: Uuid,
#[sea_orm(primary_key, auto_increment = false)] #[sea_orm(primary_key, auto_increment = false)]
pub user_id: Uuid, pub user_id: Uuid,
}
#[derive(Copy, Clone, Debug, EnumIter, DeriveRelation)]
pub enum Relation {
#[sea_orm( #[sea_orm(
belongs_to = "super::role::Entity", belongs_to,
from = "Column::RoleId", from = "role_id",
to = "super::role::Column::Id", to = "id",
on_update = "NoAction", on_update = "NoAction",
on_delete = "Cascade" on_delete = "Cascade"
)] )]
Group, pub role: HasOne<super::role::Entity>,
#[sea_orm( #[sea_orm(
belongs_to = "super::user::Entity", belongs_to,
from = "Column::UserId", from = "user_id",
to = "super::user::Column::Id", to = "id",
on_update = "NoAction", on_update = "NoAction",
on_delete = "Cascade" on_delete = "Cascade"
)] )]
User, pub user: HasOne<super::user::Entity>,
}
impl Related<super::role::Entity> for Entity {
fn to() -> RelationDef {
Relation::Group.def()
}
}
impl Related<super::user::Entity> for Entity {
fn to() -> RelationDef {
Relation::User.def()
}
} }
impl ActiveModelBehavior for ActiveModel {} impl ActiveModelBehavior for ActiveModel {}
+7 -28
View File
@@ -4,6 +4,7 @@ use sea_orm::entity::prelude::*;
use sea_orm::prelude::async_trait::async_trait; use sea_orm::prelude::async_trait::async_trait;
use sea_orm::Set; use sea_orm::Set;
#[sea_orm::model]
#[derive(Clone, Debug, PartialEq, DeriveEntityModel, Eq)] #[derive(Clone, Debug, PartialEq, DeriveEntityModel, Eq)]
#[sea_orm(table_name = "server")] #[sea_orm(table_name = "server")]
pub struct Model { pub struct Model {
@@ -15,34 +16,12 @@ pub struct Model {
pub updated_at: DateTimeUtc, pub updated_at: DateTimeUtc,
pub is_default: bool, pub is_default: bool,
pub owner_id: Option<Uuid>, pub owner_id: Option<Uuid>,
} #[sea_orm(has_many)]
pub categories: HasMany<super::category::Entity>,
#[derive(Copy, Clone, Debug, EnumIter, DeriveRelation)] #[sea_orm(has_many)]
pub enum Relation { pub channels: HasMany<super::channel::Entity>,
#[sea_orm(has_many = "super::category::Entity")] #[sea_orm(has_many)]
Category, pub server_users: HasMany<super::server_user::Entity>,
#[sea_orm(has_many = "super::channel::Entity")]
Channel,
#[sea_orm(has_many = "super::server_user::Entity")]
ServerUser,
}
impl Related<super::category::Entity> for Entity {
fn to() -> RelationDef {
Relation::Category.def()
}
}
impl Related<super::channel::Entity> for Entity {
fn to() -> RelationDef {
Relation::Channel.def()
}
}
impl Related<super::server_user::Entity> for Entity {
fn to() -> RelationDef {
Relation::ServerUser.def()
}
} }
#[async_trait] #[async_trait]
+9 -25
View File
@@ -3,6 +3,7 @@ use sea_orm::entity::prelude::*;
use sea_orm::prelude::async_trait::async_trait; use sea_orm::prelude::async_trait::async_trait;
use sea_orm::{NotSet, Set}; use sea_orm::{NotSet, Set};
#[sea_orm::model]
#[derive(Clone, Debug, PartialEq, DeriveEntityModel, Eq)] #[derive(Clone, Debug, PartialEq, DeriveEntityModel, Eq)]
#[sea_orm(table_name = "server_group_permission")] #[sea_orm(table_name = "server_group_permission")]
pub struct Model { pub struct Model {
@@ -17,39 +18,22 @@ pub struct Model {
/// Bitmask des permissions accordées directement à l'utilisateur. /// Bitmask des permissions accordées directement à l'utilisateur.
pub permission: i64, pub permission: i64,
}
#[derive(Copy, Clone, Debug, EnumIter, DeriveRelation)]
pub enum Relation {
#[sea_orm( #[sea_orm(
belongs_to = "super::server::Entity", belongs_to,
from = "Column::ServerId", from = "server_id",
to = "super::server::Column::Id", to = "id",
on_update = "NoAction", on_update = "NoAction",
on_delete = "Cascade" on_delete = "Cascade"
)] )]
Server, pub server: HasOne<super::server::Entity>,
#[sea_orm( #[sea_orm(
belongs_to = "super::role::Entity", belongs_to,
from = "Column::RoleId", from = "role_id",
to = "super::role::Column::Id", to = "id",
on_update = "NoAction", on_update = "NoAction",
on_delete = "Cascade" on_delete = "Cascade"
)] )]
Role, pub role: HasOne<super::role::Entity>,
}
impl Related<super::server::Entity> for Entity {
fn to() -> RelationDef {
Relation::Server.def()
}
}
impl Related<super::role::Entity> for Entity {
fn to() -> RelationDef {
Relation::Role.def()
}
} }
#[async_trait] #[async_trait]
+9 -24
View File
@@ -4,6 +4,7 @@ use sea_orm::entity::prelude::*;
use sea_orm::prelude::async_trait::async_trait; use sea_orm::prelude::async_trait::async_trait;
use sea_orm::Set; use sea_orm::Set;
#[sea_orm::model]
#[derive(Clone, Debug, PartialEq, DeriveEntityModel, Eq)] #[derive(Clone, Debug, PartialEq, DeriveEntityModel, Eq)]
#[sea_orm(table_name = "server_user")] #[sea_orm(table_name = "server_user")]
pub struct Model { pub struct Model {
@@ -14,38 +15,22 @@ pub struct Model {
pub username: Option<String>, pub username: Option<String>,
pub joined_at: DateTimeUtc, pub joined_at: DateTimeUtc,
pub updated_at: DateTimeUtc, pub updated_at: DateTimeUtc,
}
#[derive(Copy, Clone, Debug, EnumIter, DeriveRelation)]
pub enum Relation {
#[sea_orm( #[sea_orm(
belongs_to = "super::server::Entity", belongs_to,
from = "Column::ServerId", from = "server_id",
to = "super::server::Column::Id", to = "id",
on_update = "NoAction", on_update = "NoAction",
on_delete = "Cascade" on_delete = "Cascade"
)] )]
Server, pub server: HasOne<super::server::Entity>,
#[sea_orm( #[sea_orm(
belongs_to = "super::user::Entity", belongs_to,
from = "Column::UserId", from = "user_id",
to = "super::user::Column::Id", to = "id",
on_update = "NoAction", on_update = "NoAction",
on_delete = "Cascade" on_delete = "Cascade"
)] )]
User, pub user: HasOne<super::user::Entity>,
}
impl Related<super::server::Entity> for Entity {
fn to() -> RelationDef {
Relation::Server.def()
}
}
impl Related<super::user::Entity> for Entity {
fn to() -> RelationDef {
Relation::User.def()
}
} }
#[async_trait] #[async_trait]
+9 -25
View File
@@ -3,6 +3,7 @@ use sea_orm::entity::prelude::*;
use sea_orm::prelude::async_trait::async_trait; use sea_orm::prelude::async_trait::async_trait;
use sea_orm::{NotSet, Set}; use sea_orm::{NotSet, Set};
#[sea_orm::model]
#[derive(Clone, Debug, PartialEq, DeriveEntityModel, Eq)] #[derive(Clone, Debug, PartialEq, DeriveEntityModel, Eq)]
#[sea_orm(table_name = "server_user_permission")] #[sea_orm(table_name = "server_user_permission")]
pub struct Model { pub struct Model {
@@ -17,39 +18,22 @@ pub struct Model {
/// Bitmask des permissions accordées directement à l'utilisateur. /// Bitmask des permissions accordées directement à l'utilisateur.
pub permission: i64, pub permission: i64,
}
#[derive(Copy, Clone, Debug, EnumIter, DeriveRelation)]
pub enum Relation {
#[sea_orm( #[sea_orm(
belongs_to = "super::server::Entity", belongs_to,
from = "Column::ServerId", from = "server_id",
to = "super::server::Column::Id", to = "id",
on_update = "NoAction", on_update = "NoAction",
on_delete = "Cascade" on_delete = "Cascade"
)] )]
Server, pub server: HasOne<super::server::Entity>,
#[sea_orm( #[sea_orm(
belongs_to = "super::user::Entity", belongs_to,
from = "Column::UserId", from = "user_id",
to = "super::user::Column::Id", to = "id",
on_update = "NoAction", on_update = "NoAction",
on_delete = "Cascade" on_delete = "Cascade"
)] )]
User, pub user: HasOne<super::user::Entity>,
}
impl Related<super::server::Entity> for Entity {
fn to() -> RelationDef {
Relation::Server.def()
}
}
impl Related<super::user::Entity> for Entity {
fn to() -> RelationDef {
Relation::User.def()
}
} }
#[async_trait] #[async_trait]
+8 -28
View File
@@ -4,6 +4,8 @@ use sea_orm::entity::prelude::*;
use sea_orm::prelude::async_trait::async_trait; use sea_orm::prelude::async_trait::async_trait;
use sea_orm::Set; use sea_orm::Set;
#[sea_orm::model]
#[sea_orm(model_ex_attrs(derive(Debug)))]
#[derive(Clone, PartialEq, DeriveEntityModel, Eq)] #[derive(Clone, PartialEq, DeriveEntityModel, Eq)]
#[sea_orm(table_name = "user")] #[sea_orm(table_name = "user")]
pub struct Model { pub struct Model {
@@ -16,6 +18,12 @@ pub struct Model {
pub created_at: DateTimeUtc, pub created_at: DateTimeUtc,
pub updated_at: DateTimeUtc, pub updated_at: DateTimeUtc,
pub is_superuser: bool, pub is_superuser: bool,
#[sea_orm(has_many)]
pub channel_users: HasMany<super::channel_user::Entity>,
#[sea_orm(has_many)]
pub messages: HasMany<super::message::Entity>,
#[sea_orm(has_many)]
pub server_users: HasMany<super::server_user::Entity>,
} }
impl std::fmt::Debug for Model { impl std::fmt::Debug for Model {
@@ -32,34 +40,6 @@ impl std::fmt::Debug for Model {
} }
} }
#[derive(Copy, Clone, Debug, EnumIter, DeriveRelation)]
pub enum Relation {
#[sea_orm(has_many = "super::channel_user::Entity")]
ChannelUser,
#[sea_orm(has_many = "super::message::Entity")]
Message,
#[sea_orm(has_many = "super::server_user::Entity")]
ServerUser,
}
impl Related<super::channel_user::Entity> for Entity {
fn to() -> RelationDef {
Relation::ChannelUser.def()
}
}
impl Related<super::message::Entity> for Entity {
fn to() -> RelationDef {
Relation::Message.def()
}
}
impl Related<super::server_user::Entity> for Entity {
fn to() -> RelationDef {
Relation::ServerUser.def()
}
}
#[async_trait] #[async_trait]
impl ActiveModelBehavior for ActiveModel { impl ActiveModelBehavior for ActiveModel {
fn new() -> Self { fn new() -> Self {