Hur tänka kring att radera/DELETE en produkt som är använd?

  • Författare
  • Meddelande
Användarvisningsbild

mos

dbwebb

  • Inlägg: 11198
  • Blev medlem: 10 nov 2011, 09:52
  • Ort: Ronneby / Bankeryd

Hur tänka kring att radera/DELETE en produkt som är använd?

Inlägg05 mar 2020, 23:47

MySQL [eshop]> call delete_product("kaffe1");
ERROR 1451 (23000): Cannot delete or update a parent row: a foreign key constraint fails (eshop.stock, CONSTRAINT stock_ibfk_1 FOREIGN KEY (prod_id) REFERENCES product (id))


Bakgrunden är ett krav i databas kmom05 om CRUD av produkter i en eshop.
Skapa CRUD för att lägga till, redigera, visa och radera produkter. Du behöver enbart redigera de delar som finns i tabellen kopplad till produkten. Du behöver inte redigera antal produkter på lagret, eller kopplingen till kategori.


Du kan inte göra delete på en produkt om den finns i lagret, eller i en order, därav felmeddelandet som påpekar att du har en FK constraint där produkten du försöker radera finns i lagret.

Om du verkligen vill ta bort produkten så måste först ta bort den på lagret och alla andra platser den finns på. Detta kan du göra genom att skriva en lagrad procedur som gör det, eller genom att erbjuda ett GUI där användaren själv kan utföra radering av alla förekomster av produkten, eller implementera ON DELETE CASCADE som gör det automatiskt åt dig.

I found a solution. SET FOREIGN_KEY_CHECKS = 0; is this ok?


Nej, det är inte en bra lösning. Det ignorerar de kontroller som FK ger dig och det är en fix som leder till att din databas blir inkonsistent.

Risken med att ta bort en produkt, och alla dess förekomster, är att din databas bli logiskt korrupt eller inkonsistent. Det är normalt sett inte logiskt att ta bort orderrader på gamla ordrar, bara för att du vill radera en produkt.

Ett bra alternativ, i detta fallet, är att använda konceptet SOFT DELETE där man istället för en riktig DELETE bara markerar produkten som raderad via ett värde i en kolumn, tex en tidsstämpel. Detta förklaras i artikeln "Använd TIMESTAMP för status i databastabellen".

Man kan även tolka kravet som att "det går inte" göra DELETE på produkt om den redan är använd. Det är en tolkning som inte ger Ux på inlämningen. Du kan skriva i din redovisningstext "det var så jag tolkade kravet och jag kände att det var en rimlig avgränsning givet tid/engagement/etc".


Summering

Den rätta vägen (databasmässigt, logiskt och begreppsmässigt) är en soft delete.

När du väl har lagt till en produkt och börjat använda den i lagret/order så har den satt sina spår i databasen. Du kan inte ta bort alla dessa förekomster utan att göra din databas logiskt korrupt.

När du vill sluta använda en produkt, du tänker inte beställa den till lagret eller låta kunderna köpa den, då vill du göra den osynlig/soft deletad i systemet, du markerar den som "raderad" men du tar inte bort den. Du gör så att ditt GUI inte visar att produkten finns längre.
Men den som vill se dina gamla ordrar, där produkten köptes, kan fortfarande göra det.

Den enkla vägen tidsmässigt och för att klara kursmomentet, är att säga "när produkten är använd kan man inte göra DELETE på den, det är en begränsning i min implementation".
...
..:
.... /mos

luxaeterna

css-hackare

  • Inlägg: 26
  • Blev medlem: 12 jul 2019, 04:28

Re: Hur tänka kring att radera/DELETE en produkt som är anvä

Inlägg06 mar 2020, 00:10

Om det är någon annan som har bekymmer med konceptet soft delete så tänkte jag så här:
Jag skapade en ny kolumn i produktabellen som fungerar som "flagga", när jag sedan vill göra en så kallad "soft-delete" så markerar jag helt enkelt produkten som raderad tex. genom att göra en insert eller update i flaggkolumnen för produkten, tex med värdet "d" för deleted. Därefter kan en enkelt gömma produkterna som är flaggade som deleted från användarnas vy genom att lägga till ett where condition som endast visar rader som innehåller "null" eller inte är flaggade med "d".

Finns säkert andra sätt att göra på det också, men det var så här jag gjorde. Hoppas det kan hjälpa någon.

ejessyp

på gång

  • Inlägg: 2
  • Blev medlem: 30 okt 2019, 14:08

Re: Hur tänka kring att radera/DELETE en produkt som är anvä

Inlägg06 mar 2020, 13:33

I added a timestamp (a new column named "deleted" to the product). Then it works like a soft delete flag.

Vilka är online

Användare som besöker denna kategori: Inga registrerade användare och 5 gäster