]> git.mxchange.org Git - friendica.git/blob - src/Core/Lock/DatabaseLockDriver.php
code standards / simplifications
[friendica.git] / src / Core / Lock / DatabaseLockDriver.php
1 <?php
2
3 namespace Friendica\Core\Lock;
4
5 use dba;
6 use Friendica\Database\DBM;
7 use Friendica\Util\DateTimeFormat;
8
9 /**
10  * Locking driver that stores the locks in the database
11  */
12 class DatabaseLockDriver extends AbstractLockDriver
13 {
14         /**
15          * (@inheritdoc)
16          */
17         public function acquire($key, $timeout = 120)
18         {
19                 $got_lock = false;
20                 $start = time();
21
22                 do {
23                         dba::lock('locks');
24                         $lock = dba::selectFirst('locks', ['locked', 'pid'], ['`name` = ? AND `expires` >= ?', $key, DateTimeFormat::utcNow()]);
25
26                         if (DBM::is_result($lock)) {
27                                 if ($lock['locked']) {
28                                         // We want to lock something that was already locked by us? So we got the lock.
29                                         if ($lock['pid'] == getmypid()) {
30                                                 $got_lock = true;
31                                                 $this->markAcquire($key);
32                                         }
33                                 }
34                                 if (!$lock['locked']) {
35                                         dba::update('locks', ['locked' => true, 'pid' => getmypid(), 'expires' => DateTimeFormat::utc('now + 300seconds')], ['name' => $key]);
36                                         $got_lock = true;
37                                         $this->markAcquire($key);
38                                 }
39                         } else {
40                                 dba::insert('locks', ['name' => $key, 'locked' => true, 'pid' => getmypid(), 'expires' => DateTimeFormat::utc('now + 300seconds')]);
41                                 $got_lock = true;
42                                 $this->markAcquire($key);
43                         }
44
45                         dba::unlock();
46
47                         if (!$got_lock && ($timeout > 0)) {
48                                 usleep(rand(100000, 2000000));
49                         }
50                 } while (!$got_lock && ((time() - $start) < $timeout));
51
52                 return $got_lock;
53         }
54
55         /**
56          * (@inheritdoc)
57          */
58         public function release($key)
59         {
60                 dba::delete('locks', ['name' => $key, 'pid' => getmypid()]);
61
62                 $this->markRelease($key);
63
64                 return;
65         }
66
67         /**
68          * (@inheritdoc)
69          */
70         public function releaseAll()
71         {
72                 dba::delete('locks', ['pid' => getmypid()]);
73
74                 $this->acquiredLocks = [];
75         }
76
77         /**
78          * (@inheritdoc)
79          */
80         public function isLocked($key)
81         {
82                 $lock = dba::selectFirst('locks', ['locked'], ['`name` = ? AND `expires` >= ?', $key, DateTimeFormat::utcNow()]);
83
84                 if (DBM::is_result($lock)) {
85                         return $lock['locked'] !== false;
86                 } else {
87                         return false;
88                 }
89         }
90 }