Vă mulțumim pentru susținere

Editarea înregistrărilor bazei de date de către mai mulți utilizatori

Am proiectat tabele de baze de date (normalizate, pe un server MS SQL) și am creat un capăt frontal independent pentru o aplicație care va fi utilizată de o mână de utilizatori pentru a adăuga și edita informații. Vom adăuga o interfață web care să permită căutarea în zona noastră de producție la o dată ulterioară.

Sunt îngrijorat de faptul că, dacă doi utilizatori încep să editeze aceeași înregistrare, atunci ultima pentru a se angaja actualizarea ar fi "câștigătorul" și informațiile importante ar putea fi pierdute. O serie de soluții vin în minte, dar nu sunt sigur dacă voi crea o durere de cap mai mare.

  1. Do nothing and hope that two users are never going to be editing the same record at the same time. - Might never happed but what if it does?
  2. Editing routine could store a copy of the original data as well as the updates and then compare when the user has finished editing. If they differ show user and comfirm update - Would require two copies of data to be stored.
  3. Add last updated DATETIME column and check it matches when we update, if not then show differences. - requires new column in each of the relevant tables.
  4. Create an editing table that registers when users start editing a record that will be checked and prevent other users from editing same record. - would require carful thought of program flow to prevent deadlocks and records becoming locked if a user crashes out of the program.

Există soluții mai bune sau ar trebui să mă duc la una dintre acestea?

0
adăugat editat

7 răspunsuri

Baza de date va face acest lucru pentru dvs. Uită-te la "select ... pentru actualizare", care este proiectat doar pentru acest gen de lucruri. Acesta vă va oferi o blocare de scriere pe rândurile selectate, pe care le puteți apoi angaja sau revine.

0
adăugat

Dacă vă așteptați la coliziuni rare, Concurrency optimist este probabil cel mai bun pariu.

Scott Mitchell wrote a comprehensive tutorial on implementing that pattern:
Implementing Optimistic Concurrency

0
adăugat
Vă mulțumim pentru partajare.
adăugat autor Pramod Gharu

@ Mark Harrison: SQL Server nu acceptă această sintaxă ( SELECT ... FOR UPDATE ).

Echivalentul SQL Server este instrucțiunea SELECT sugestie UPDLOCK .

Consultați SQL Server Books Online pentru mai multe informații.

0
adăugat

O altă opțiune este să testați că valorile din înregistrarea pe care o modificați sunt încă la fel ca atunci când ați început:

SELECT 
    customer_nm,
    customer_nm AS customer_nm_orig
FROM demo_customer
WHERE customer_id = @p_customer_id

(afișați câmpul client_nm și utilizatorul îl modifică)

UPDATE demo_customer
SET customer_nm = @p_customer_name_new
WHERE customer_id = @p_customer_id
AND customer_name = @p_customer_nm_old

IF @@ROWCOUNT = 0
    RAISERROR( 'Update failed: Data changed' );

Nu trebuie să adăugați o coloană nouă în tabel (și să o actualizați), dar trebuie să creați mai multe instrucțiuni SQL detaliate și să treci noi și vechi la procedura memorată.

De asemenea, are avantajul că nu închideți înregistrările - pentru că știm cu toții că înregistrările vor rămâne blocate când nu ar trebui să fie ...

0
adăugat

O abordare clasică este după cum urmează:

  • add a boolean field , "locked" to each table.
  • set this to false by default.
  • when a user starts editing, you do this:

    • lock the row (or the whole table if you can't lock the row)
    • check the flag on the row you want to edit
    • if the flag is true then
      • inform the user that they cannot edit that row at the moment
    • else
      • set the flag to true
    • release the lock

    • when saving the record, set the flag back to false

0
adăugat
Acest lucru nu este bine enought, dacă setați lock = true, în cazul în care aplicația sau browser-ul este accident, atunci înregistrarea este blocat pentru totdeauna.
adăugat autor Cheung
Acest val de soluție de pavilion alb "rezolvarea modificărilor concurente este greu, așa că am de gând să renunțe"
adăugat autor Chris Marisic
Bun punct, @SilverNight - poți posta soluția corectă?
adăugat autor AJ.
Pentru astfel de cazuri (aplicație / accident de browser), puteți adăuga metoda ForceUnlock la aplicație, care va seta forțat blocarea la False.
adăugat autor Oleksandr

Cu mine, cel mai bun mod de a avea o coloană lastupdate (timetamp datatype). când selectați și actualizați doar comparați această valoare un alt avantaj al acestei soluții este că puteți utiliza această coloană pentru a urmări datele schimbate de timp. Cred că nu este bine dacă creați un colum ca isLock pentru actualizarea cecului.

0
adăugat

-first create filed (update time) to store last update record -when any user select record save select time, compare between select time and update time field if( update time) > (select time) that mean another user update this record after select record

0
adăugat