Database locking

michele.b26

Nuovo Utente
18 Dic 2008
27
0
0
Ciao a tutti, vorrei sapere se c'è in PHP il modo di attivare e disattivare un lock sul database.

Quello che mi serve è fare due query in modo atomico in modo che nessun altro utente possa leggere o scrivere nel database durante l'esecuzione di queste due.

Ad esempio se voglio fare un contatore del tipo:

PHP:
lock($database); //lock del database

$query = "SELECT counter FROM contatore";

$query = mysql_query($query)
	or die("Query non eseguita: " . mysql_error());

$num = mysql_fetch_array($query, MYSQL_NUM);

$num[0]++;

$query = "UPDATE contatore SET counter=$num[0] WHERE id_contatore=$id";

$query = mysql_query($query)
	or die("Query non eseguita: " . mysql_error());

unlock($database); //rilascio del lock

mi servirebbe il codice per le due funzioni ”lock” e "unlock”, sempre che esista, e in tal caso come si potrebbe aggirare l'ostacolo?

Grazie per ogni aiuto.
 
Ciao,
hai provato così?

PHP:
$query = "LOCK TABLES contatore WRITE";
$query = mysql_query($query) 
    or die("Query non eseguita: " . mysql_error()); 

$query = "SELECT counter FROM contatore"; 
$query = mysql_query($query) 
    or die("Query non eseguita: " . mysql_error()); 

$num = mysql_fetch_array($query, MYSQL_NUM); 

$num[0]++; 

$query = "UPDATE contatore SET counter=$num[0] WHERE id_contatore=$id"; 

$query = mysql_query($query) 
    or die("Query non eseguita: " . mysql_error()); 

$query = "UNLOCK TABLES";
$query = mysql_query($query) 
    or die("Query non eseguita: " . mysql_error());

Alessandro
 
Tieni conto che per poter definire un lock su una tabella l'utente con cui ti connetti a MySQL deve possedere i permessi necessari; per il resto basta seguire i consigli di Magicale.
 
Ciao,
hai provato così?

PHP:
$query = "LOCK TABLES contatore WRITE";
$query = mysql_query($query) 
    or die("Query non eseguita: " . mysql_error()); 

$query = "SELECT counter FROM contatore"; 
$query = mysql_query($query) 
    or die("Query non eseguita: " . mysql_error()); 

$num = mysql_fetch_array($query, MYSQL_NUM); 

$num[0]++; 

$query = "UPDATE contatore SET counter=$num[0] WHERE id_contatore=$id"; 

$query = mysql_query($query) 
    or die("Query non eseguita: " . mysql_error()); 

$query = "UNLOCK TABLES";
$query = mysql_query($query) 
    or die("Query non eseguita: " . mysql_error());

Alessandro

No, non conoscevo la sintassi :-) ma questo è un lock in sola scrittura? Mi servirebbe anche in lettua non c'è?

Il motivo è per il classico giochino:

supponiamo che Alice legga il contatore e abbia il numero 3 in $num, allo stesso tempo legge anche Bob e ottiene 3, poi Alice blocca in scrittura, aggiunge 1 a $num e lo scrive nel database, poi rilascia il lock, a questo punto anche Bob blocca la tabella e scrive 4 nel DB, così facendo ho perso un punto, dovrei avere 5 e invece ho 4.

Vi ringrazio per ogni delucidazione.
 
Ciao,
per quel tipo di porblema non è necessario che leggi il dato prima dell'update.

Puoi fare così per incrementare il contatore:
Codice:
$query = "UPDATE contatore SET counter=counter+1 WHERE id_contatore=$id";

EDIT: Se non ricordo male, il blocco WRITE, blocca sia in lettura che scrittura.

Alessandro
 
Ultima modifica:

Discussioni simili