Update and Delete Resources
Learn to update and delete a resource in Diesel.
Update
Updating a resource might be a bit tricky, so we’re going to need a few helper structs. We’ll use the annotation AsChangeset
for the struct
we directly modify in the database.
We have the option to refactor the structs used for inserting, but in our case, we’ll create new ones for this purpose.
Press + to interact
#[derive(Insertable, Queryable, AsChangeset, Debug, Clone, Serialize, Deserialize)]#[table_name="variants"]pub struct FormVariant {pub id: Option<i32>,pub name: String}#[derive(Insertable, Debug, AsChangeset)]#[table_name="products_variants"]pub struct FormProductVariant {pub id: Option<i32>,pub variant_id: Option<i32>,pub product_id: i32,pub value: Option<String>}pub struct FormProductVariantComplete {pub variant: Option<FormVariant>,pub product_variant: FormProductVariant,}pub struct FormProduct {pub product: NewProduct,pub variants: Vec<FormProductVariantComplete>}
Next, it’s time for the code to update the product.
Press + to interact
#[macro_use]extern crate diesel;use diesel::{SqliteConnection, Connection, QueryDsl, RunQueryDsl};use anyhow::Result;use ::shoe_store::models::FormProduct;no_arg_sql_function!(last_insert_rowid, diesel::sql_types::Integer);fn update_product(product_id: i32, form_product: FormProduct, conn: &SqliteConnection) -> Result<i32> {use ::shoe_store::schema::products::dsl::products;use ::shoe_store::schema::variants;use ::shoe_store::schema::products_variants::dsl::products_variants;// We begin a transaction, just to make sure everything runs successfullyconn.transaction(|| {diesel::update(products.find(product_id)).set(&form_product.product).execute(conn)?;// We just loop through all variants availablefor mut form_product_variant in form_product.variants {// If there's no variant id, we probably need to insert a new one.if form_product_variant.product_variant.variant_id.is_none() {diesel::insert_into(variants::dsl::variants).values(form_product_variant.variant).execute(conn)?;let last_variant_id: i32 =diesel::select(last_insert_rowid).first(conn)?;form_product_variant.product_variant.variant_id = Some(last_variant_id);}// We have an id, so we should update the variant product.if let Some(product_variant_id) = form_product_variant.product_variant.id {diesel::update(products_variants.find(product_variant_id)).set(&form_product_variant.product_variant).execute(conn)?;}}Ok(product_id)})}
We start updating the ...