From 534d819865dfe4645aca0c373dfdce0eb2915d80 Mon Sep 17 00:00:00 2001 From: Peter Schiwy Date: Mon, 3 Jun 2024 15:41:00 +0200 Subject: [PATCH] =?UTF-8?q?Modelle=20hinzugef=C3=BCgt?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- migrations/20240530193519_typen.up.sql | 2 +- migrations/20240530193528_hersteller.up.sql | 2 +- migrations/20240530193533_modelle.up.sql | 6 +- src/models/mod.rs | 1 - src/models/modell.rs | 107 +++++++++++++------- src/models/modell_temp.rs | 44 -------- src/models/typ.rs | 2 +- src/mutations/mod.rs | 8 +- src/mutations/modell.rs | 35 +++++++ src/queries/mod.rs | 2 - src/queries/modell.rs | 21 ++-- src/queries/modell_temp.rs | 22 ---- 12 files changed, 122 insertions(+), 130 deletions(-) delete mode 100644 src/models/modell_temp.rs create mode 100644 src/mutations/modell.rs delete mode 100644 src/queries/modell_temp.rs diff --git a/migrations/20240530193519_typen.up.sql b/migrations/20240530193519_typen.up.sql index bb728f5..7eb3eec 100644 --- a/migrations/20240530193519_typen.up.sql +++ b/migrations/20240530193519_typen.up.sql @@ -1,5 +1,5 @@ -- Add up migration script here -CREATE TABLE typen ( +CREATE TABLE IF NOT EXISTS typen ( typ_id SERIAL PRIMARY KEY, name VARCHAR NOT NULL ); diff --git a/migrations/20240530193528_hersteller.up.sql b/migrations/20240530193528_hersteller.up.sql index 105cbf6..227d36b 100644 --- a/migrations/20240530193528_hersteller.up.sql +++ b/migrations/20240530193528_hersteller.up.sql @@ -1,5 +1,5 @@ -- Add up migration script here -CREATE TABLE hersteller ( +CREATE TABLE IF NOT EXISTS hersteller ( hersteller_id SERIAL PRIMARY KEY, name VARCHAR NOT NULL ); diff --git a/migrations/20240530193533_modelle.up.sql b/migrations/20240530193533_modelle.up.sql index 5fcae37..ed55bca 100644 --- a/migrations/20240530193533_modelle.up.sql +++ b/migrations/20240530193533_modelle.up.sql @@ -1,9 +1,9 @@ -- Add up migration script here -CREATE TABLE modelle ( +CREATE TABLE IF NOT EXISTS modelle ( modell_id SERIAL PRIMARY KEY, name VARCHAR NOT NULL, typ_id SERIAL, hersteller_id SERIAL, - CONSTRAINT fk_typ FOREIGN KEY(typ_id) REFERENCES typen(typ_id), - CONSTRAINT fk_hersteller FOREIGN KEY (hersteller_id) REFERENCES hersteller(hersteller_id) + CONSTRAINT fk_typ FOREIGN KEY(typ_id) REFERENCES typen(typ_id) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT fk_hersteller FOREIGN KEY (hersteller_id) REFERENCES hersteller(hersteller_id) ON DELETE NO ACTION ON UPDATE NO ACTION ) diff --git a/src/models/mod.rs b/src/models/mod.rs index da6ad95..5a3235d 100644 --- a/src/models/mod.rs +++ b/src/models/mod.rs @@ -1,4 +1,3 @@ pub mod hersteller; pub mod modell; -pub mod modell_temp; pub mod typ; diff --git a/src/models/modell.rs b/src/models/modell.rs index fd0a4dd..08a5ded 100644 --- a/src/models/modell.rs +++ b/src/models/modell.rs @@ -1,81 +1,112 @@ use anyhow::Result; -use async_graphql::SimpleObject; +use async_graphql::{InputObject, SimpleObject}; use serde::{Deserialize, Serialize}; use sqlx::{FromRow, PgPool}; +use super::{hersteller::Hersteller, typ::Typ}; + #[derive(SimpleObject, FromRow, Deserialize, Serialize)] pub struct Modell { /// Die Datenbank-ID pub modell_id: i32, - /// Der Typ - typ_id: i32, + /// Der Geräte-Typ z.B. Monitor + typ: Typ, - /// Der Hersteller - hersteller_id: i32, + /// Der Geräte-Hersteller z.B. Dell + hersteller: Hersteller, /// Der Name eines Modells name: String, } +#[derive(InputObject)] +pub struct ModellCreateInput { + pub name: String, + pub typ_id: i32, + pub hersteller_id: i32, +} + +#[derive(InputObject)] +pub struct ModellUpdateInput { + pub modell_id: i32, + pub name: Option, + pub typ_id: Option, + pub hersteller_id: Option, +} + impl Modell { - pub async fn create( - pool: &PgPool, - typ_id: i32, - hersteller_id: i32, - name: &str, - ) -> Result { - let row = sqlx::query!( - "INSERT INTO modelle(typ_id, hersteller_id, name) VALUES ($1, $2, $3) RETURNING modell_id", - typ_id, - hersteller_id, - name + pub async fn read_one(pool: &PgPool, id: &i32) -> Result { + let row = sqlx::query_as!( + Modell, + r#" + select + m.modell_id, m.name, + (t.typ_id, t.name) as "typ!: Typ", + (h.hersteller_id, h.name) as "hersteller!: Hersteller" + from modelle as m + join typen as t using(typ_id) + join hersteller as h using(hersteller_id) + where m.modell_id = $1; + "#, + id ) .fetch_one(pool) .await?; - Ok(Modell { - modell_id: row.modell_id, - typ_id, - hersteller_id, - name: name.to_string(), - }) - } - - pub async fn read_one(pool: &PgPool, id: &i32) -> Result { - let row = sqlx::query_as!(Modell, "SELECT * FROM modelle WHERE modell_id = $1", id) - .fetch_one(pool) - .await?; - Ok(row) } pub async fn read_all(pool: &PgPool) -> Result> { - let rows = sqlx::query_as!( + let row = sqlx::query_as!( Modell, - "SELECT modell_id, name, hersteller_id, typ_id FROM modelle" + r#" + select + m.modell_id, m.name, + (t.typ_id, t.name) as "typ!: Typ", + (h.hersteller_id, h.name) as "hersteller!: Hersteller" + from modelle as m + join typen as t using(typ_id) + join hersteller as h using(hersteller_id) + "# ) .fetch_all(pool) .await?; - Ok(rows) + Ok(row) } - pub async fn update(pool: &PgPool, id: &i32, name: &str) -> Result { - sqlx::query!("UPDATE modelle SET name=$1 WHERE modell_id = $2", name, id) - .execute(pool) - .await?; + pub async fn create(pool: &PgPool, input: &ModellCreateInput) -> Result { + let row = sqlx::query!(r#"INSERT INTO modelle(typ_id, hersteller_id, name) VALUES ($1, $2, $3) RETURNING modell_id"#, input.typ_id, input.hersteller_id, input.name + ) + .fetch_one(pool) + .await?; - let t = Modell::read_one(pool, id).await?; + Self::read_one(pool, &row.modell_id).await + } + + pub async fn update(pool: &PgPool, input: &ModellUpdateInput) -> Result { + sqlx::query!( + "UPDATE modelle SET name=COALESCE($1, name), typ_id=COALESCE($2, typ_id), hersteller_id=COALESCE($3, hersteller_id) WHERE modell_id = $4", + input.name, + input.typ_id, + input.hersteller_id, + input.modell_id + ) + .execute(pool) + .await?; + + let t = Modell::read_one(pool, &input.modell_id).await?; Ok(t) } pub async fn delete(pool: &PgPool, id: &i32) -> Result<()> { - sqlx::query!("DELETE FROM modelle WHERE modell_id = $1", id) + let result = sqlx::query!("DELETE FROM modelle WHERE modell_id = $1", id) .execute(pool) .await?; + println!("{:#?}", result); Ok(()) } } diff --git a/src/models/modell_temp.rs b/src/models/modell_temp.rs deleted file mode 100644 index b73365f..0000000 --- a/src/models/modell_temp.rs +++ /dev/null @@ -1,44 +0,0 @@ -use anyhow::Result; -use async_graphql::SimpleObject; -use serde::{Deserialize, Serialize}; -use sqlx::{FromRow, PgPool}; - -use super::{hersteller::Hersteller, typ::Typ}; - -#[derive(SimpleObject, Debug, FromRow, Deserialize, Serialize)] -pub struct ModellTemp { - /// Die Datenbank-ID - pub modell_id: i32, - - /// Der Typ - pub typ: Typ, - - /// Der Hersteller - pub hersteller: Hersteller, - - /// Der Name eines Modells - pub name: String, -} - -impl ModellTemp { - pub async fn read_one(pool: &PgPool, id: &i32) -> Result { - let row = sqlx::query_as!( - ModellTemp, - r#" - select - m.modell_id, m.name, - (t.typ_id, t.name) as "typ!: Typ", - (h.hersteller_id, h.name) as "hersteller!: Hersteller" - from modelle as m - join typen as t using(typ_id) - join hersteller as h using(hersteller_id) - where m.modell_id = $1; - "#, - id - ) - .fetch_one(pool) - .await?; - - Ok(row) - } -} diff --git a/src/models/typ.rs b/src/models/typ.rs index bef13c9..68d584a 100644 --- a/src/models/typ.rs +++ b/src/models/typ.rs @@ -7,7 +7,7 @@ use sqlx::{FromRow, PgPool, Type}; pub struct Typ { pub typ_id: i32, - /// Der Name eines Typs + /// Name eines Typs pub name: String, } diff --git a/src/mutations/mod.rs b/src/mutations/mod.rs index 033b876..bf1760c 100644 --- a/src/mutations/mod.rs +++ b/src/mutations/mod.rs @@ -1,7 +1,11 @@ pub mod hersteller; +pub mod modell; pub mod typ; - use async_graphql::MergedObject; #[derive(MergedObject, Default)] -pub struct Mutation(typ::TypMutation, hersteller::HerstellerMutation); +pub struct Mutation( + typ::TypMutation, + hersteller::HerstellerMutation, + modell::ModellMutation, +); diff --git a/src/mutations/modell.rs b/src/mutations/modell.rs new file mode 100644 index 0000000..74a0b44 --- /dev/null +++ b/src/mutations/modell.rs @@ -0,0 +1,35 @@ +use crate::models::modell::*; +use async_graphql::{Context, FieldResult}; +use sqlx::postgres::PgPool; + +#[derive(Default)] +pub struct ModellMutation; + +#[async_graphql::Object] +impl ModellMutation { + async fn create_modell( + &self, + ctx: &Context<'_>, + modell: ModellCreateInput, + ) -> FieldResult { + let pool = ctx.data::()?; + let row = Modell::create(pool, &modell).await?; + Ok(row) + } + + async fn update_modell( + &self, + ctx: &Context<'_>, + modell: ModellUpdateInput, + ) -> FieldResult { + let pool = ctx.data::()?; + let row = Modell::update(pool, &modell).await?; + Ok(row) + } + async fn delete_typ(&self, ctx: &Context<'_>, id: i32) -> FieldResult { + let pool = ctx.data::()?; + + Modell::delete(pool, &id).await?; + Ok(true) + } +} diff --git a/src/queries/mod.rs b/src/queries/mod.rs index 1bbb38c..1703ea0 100644 --- a/src/queries/mod.rs +++ b/src/queries/mod.rs @@ -1,6 +1,5 @@ pub mod hersteller; pub mod modell; -pub mod modell_temp; pub mod typ; use async_graphql::MergedObject; @@ -9,6 +8,5 @@ use async_graphql::MergedObject; pub struct Query( typ::TypQuery, modell::ModellQuery, - modell_temp::ModellTempQuery, hersteller::HerstellerQuery, ); diff --git a/src/queries/modell.rs b/src/queries/modell.rs index eb75f43..a0fd573 100644 --- a/src/queries/modell.rs +++ b/src/queries/modell.rs @@ -10,25 +10,16 @@ pub struct ModellQuery { #[Object(extends)] impl ModellQuery { - // #[graphql(external)] - // async fn id(&self) -> &i32 { - // &self.id - // } - - async fn modelle<'a>(&self, ctx: &'a Context<'_>) -> FieldResult> { - let pool = ctx.data::()?; - let rows = Modell::read_all(pool).await?; - Ok(rows) - } - async fn modell<'a>(&self, ctx: &'a Context<'_>, id: i32) -> FieldResult { let pool = ctx.data::()?; let row = Modell::read_one(pool, &id).await?; Ok(row) } - // #[graphql(entity)] - // async fn find_modell_by_id(&self, id: i32) -> Modell { - // Modell { id } - // } + async fn modelle<'a>(&self, ctx: &'a Context<'_>) -> FieldResult> { + let pool = ctx.data::()?; + let output = Modell::read_all(pool).await?; + + Ok(output) + } } diff --git a/src/queries/modell_temp.rs b/src/queries/modell_temp.rs deleted file mode 100644 index 5aec0a1..0000000 --- a/src/queries/modell_temp.rs +++ /dev/null @@ -1,22 +0,0 @@ -use async_graphql::{Context, FieldResult, Object}; -use sqlx::postgres::PgPool; - -use crate::models::modell_temp::ModellTemp; - -#[derive(Default)] -pub struct ModellTempQuery {} - -#[Object(extends)] -impl ModellTempQuery { - // async fn modelle<'a>(&self, ctx: &'a Context<'_>) -> FieldResult> { - // let pool = ctx.data::()?; - // let rows = ModellTemp::read_all(pool).await?; - // Ok(rows) - // } - - async fn modell_temp<'a>(&self, ctx: &'a Context<'_>, id: i32) -> FieldResult { - let pool = ctx.data::()?; - let row = ModellTemp::read_one(pool, &id).await?; - Ok(row) - } -}