Italian sql, blocco record

LordZenzo

Well-Known Member
Licensed User
Longtime User
per i guru, ditemi se sbaglio
ho una tabella 'mercato' con campi nome,citta,bene,prezzo,quanti,data

ipotizando che due utenti vogliano agire sullo stesso record contemporaneamente si crea casino
perché per 'agire' impiegano del tempo, quindi leggono il record, pensano, agiscono
e nel frattempo qualcun altro a agito sullo stesso record

pensavo ad un blocco a livello di record ma non so come fare con php, anche perche per leggere e per scrivete uso due diversi fole php
cosi ho pensato di modificare il record in fase di lettura, variando il solo campo città

il pensiero è che se due utenti tentano la stessa operazione contemporaneamente, uno dei due fallisce perché trova il record gia cambiato, ossia, il comando update citta=pinco in citta=lok'pinco viene eseguito una sola volta, il primo a di ritorno 1 record variato, il secondo 0 record variati

penso bene?
 

LucaMs

Expert
Licensed User
Longtime User
Va beh, avevo deciso di asteneremi dallo scrivere ancora in questo sito, dato lo scarso apprezzamento (eufemisfmo) ma almeno agli italiani non riesco a non rispondere.

Penso che dovresti aggiungere un campo, anche di un solo bit, ad ogni record ed usarlo per far sapere agli utenti che il record in questione è già nelle mani altrui (lo imposti ad 1 quando un utente sta modificando il record e quindi chiunque voglia fare altrettanto deve prima verificare che questo campo abbia valore 0).
 

LordZenzo

Well-Known Member
Licensed User
Longtime User
Penso che dovresti aggiungere un campo, anche di un solo bit, ad ogni record ed usarlo per far sapere agli utenti che il record in questione è già nelle mani altrui (lo imposti ad 1 quando un utente sta modificando il record e quindi chiunque voglia fare altrettanto deve prima verificare che questo campo abbia valore 0).
be in pratica faccio lo stesso modificando il campo citta , il mio dubbio è, il server compie una sola azione per volta anche senza blocco del record? bo....
 

ronin69

Member
Licensed User
Longtime User
Tendenzialmente si lascia al Database la gestione della concorrenza. Il tuo peraltro è un caso classico.
Gestirla a mano è sempre problematico/difficile.

Comunque dipende dal Database molto. C'è letteratura in giro da leggere e il caso è stato risolto 1000 volte . Ovviamente io non ricordo come (e pensare che nel 92 passai l'esame a 26)
 

udg

Expert
Licensed User
Longtime User
Aggiungerei che il lock manuale ha un altro "pericolo". Cosa succede se l'utente che ha posto il lock si disconnette o comunque non effettua l'operazione che ha come conseguenza lo sblocco del lock?
 

LordZenzo

Well-Known Member
Licensed User
Longtime User
Cosa succede se l'utente che ha posto il lock si disconnette o comunque non effettua l'operazione che ha come conseguenza lo sblocco del lock?
in effetti questo era uno dei problemi che mi ponevo, alla fine la soluzione che ho adottato mi pare la piu semplice, nessun blocco, nessuna perdita di dati, al massimo ogni tanto un po di manutenzione per togliere i 'lok' di troppo
 

sirjo66

Well-Known Member
Licensed User
Longtime User
uno dei sistemi più semplici per il "lock" dei record (anche se in realtà questo sistema non locka nulla) è il sistema che utilizza i TimeStamp

su ogni record aggiungi il campo TimeStamp che conterrà data, ora (compreso secondi e millisecondi) dell'ultimo aggiornamento del record.
Dovrai quindi fare che il server, ogni volta che scrive su quel record, aggiorna il campo TimeStamp con i dati prelevati dall'orologio del server stesso.

Il client quindi, quando vuole modificare un record, lo legge in memoria e lo mostra a video all'utente che ci farà tutte le modifiche del caso.
Quando l'utente preme "conferma modifiche" il client andrà ad aggiornare il record sul server SOLAMENTE se il TimeStamp che ha in memoria è uguale a quello che è ancora sul server stesso
(qui hai due possibilità per fare questo controllo, prima possibilità leggi di nuovo il record e così leggi se TimeStamp è stato modificato, oppure l'altra possibilità è di far fare il controllo al server stesso)
Se trovi che il TimeStamp è uguale a quello che hai in memoria aggiorni il record (e anche il TimeStamp) altrimenti fai uscire un avviso all'utente dicendo che nel frattempo qualcun altro ha modif
 

LordZenzo

Well-Known Member
Licensed User
Longtime User

sirjo66

Well-Known Member
Licensed User
Longtime User
nella definizione della tua tabella aggiungi un campo (chiamalo come vuoi) e come tipo di dato gli dici che è un TIMESTAMP

poi, nella definizione di questo campo dovrai mettere DEFAULT = CURRENT_TIMESTAMP e anche ON UPDATE = CURRENT_TIMESTAMP

in questo modo, quando crei un nuovo record o aggiorni un record metterà il timestamp in automatico su questo campo

guarda qui:
https://dev.mysql.com/doc/refman/5.6/en/timestamp-initialization.html
 
Last edited:

LucaMs

Expert
Licensed User
Longtime User
C'è anche un altro piccolo problema; la data/ora registrata (timestamp) sarà quella del server (dove sarà?): come confrontarla con quella del client (che potrebbe stare in Cina o a Milano?)

Io, per scopi diversi, uso una data UTC.
 

sirjo66

Well-Known Member
Licensed User
Longtime User
ad esempio:

CREATE TABLE `test` (
`name` varchar(30) NOT NULL,
`modified` TIMESTAMP(4) DEFAULT CURRENT_TIMESTAMP(4) ON UPDATE CURRENT_TIMESTAMP(4)
) ENGINE='MyISAM';


non importa se sei in cina o a Milano, devi solo leggere il TimeStamp, tenerlo in memoria, e permettere l'aggiornamento del record solo se il TimeStamp non è stato modificato, non importa a che valore è impostato
 
Top