What is the principle of adding memory lock to PHP lottery event? How to implement it?
public function acquire($key) {
//If you need to acquire two locks at the same time
if ( is_array($key) && count($key) == 2 ) {
while (TRUE) {
$res = array();
foreach($key as $k => $v) {
$res[$k] = $this->acquire($v);
if ( !$res[$k] ) {
break;
}
}
//If the first lock is not obtained, return directly
if ( !$res[0] ) {
$err = new SysErr(System::MEMCACHE_ACQUIRE_LOCK_ERROR);
ErrorHandle::throwErr($err);
} elseif( !$res[1] ) {
//Release the first lock, wait and try again
$this->release($key[0]);
usleep(LockConfig::LOCK_TIMEWAIT);
} else {
return TRUE;
}
}
} else {
$lock_key = LockConfig::LOCK_PREFIX . $key;
$i = 0;
do {
$lock = $this->_memcache->add( $lock_key, 1, LockConfig::LOCK_TIMEOUT );
//If the lock is not obtained for the first time, wait for the specified time and try again.
if ($i > 0) {
usleep(LockConfig::LOCK_TIMEWAIT);
}
$i++;
//Exit after exceeding the number of retries
if ($i > LockConfig::LOCK_RETRY_TIMES) {
$err = new SysErr(System::MEMCACHE_ACQUIRE_LOCK_ERROR);
ErrorHandle::throwErr($err);
}
} while( !$lock );
// record log
if ($i > 1) {
LogHelper::warning('lock.log', "Acquire lock '{$lock_key}' for {$i} times");
}
return $lock;
}
}
/**
* Release memory lock
*
* @param string $key The key value after removing the prefix of the memory lock
* @return bool Returns TRUE if released successfully
*/
public function release($key) {
$lock_key = LockConfig::LOCK_PREFIX . $key;
return $this->_memcache->delete($lock_key);
}
You don’t need the memory lock for the lottery. It should be possible to use a Redis queue or transaction and add a Mysql lock. .
I don’t know if the memory lock you want is this:
$lock = new CacheLock('key_name');
$lock->lock();
//logic here
$lock->unlock();
CacheLock process lock is mainly used for single-process cache acquisition when the cache fails to prevent excessive SQL requests from penetrating into the database. It is used to solve the lock control of PHP during concurrency and inter-process locking through file/eaccelerator. If not Use eaccelerator to process file locks, and generate locks with corresponding granularity in the corresponding directory. Using eaccelerator, processing is done in memory, and the performance is relatively high. Different locks are executed in parallel, similar to the row-level locks of mysql innodb.