Skip to content

Commit 792b27e

Browse files
committed
Merge pull request #93 from dovg/sequenceCacheOneCommit
* + Sequential cache. See changelog for details
2 parents 4c9e201 + bf59a44 commit 792b27e

File tree

8 files changed

+362
-54
lines changed

8 files changed

+362
-54
lines changed

.gitignore

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,3 +7,5 @@ test/meta/Proto/
77
test/main/data/urls/parser.dump.new
88
.idea
99
test/onphp
10+
/nbproject/
11+

core/Base/Assert.class.php

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -277,6 +277,14 @@ public static function isUnreachable($message = 'unreachable code reached')
277277
throw new WrongArgumentException($message);
278278
}
279279

280+
public static function isObject($object, $message = null)
281+
{
282+
if (!is_object($object))
283+
throw new WrongArgumentException(
284+
$message.' not object given'
285+
);
286+
}
287+
280288
/// exceptionless methods
281289
//@{
282290
public static function checkInteger($value)

core/Cache/PeclMemcached.class.php

Lines changed: 86 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
<?php
22
/***************************************************************************
3-
* Copyright (C) 2006-2008 by Konstantin V. Arkhipov *
3+
* Copyright (C) 2006-2012 by Konstantin V. Arkhipov *
44
* *
55
* This program is free software; you can redistribute it and/or modify *
66
* it under the terms of the GNU Lesser General Public License as *
@@ -21,38 +21,36 @@ class PeclMemcached extends CachePeer
2121
{
2222
const DEFAULT_PORT = 11211;
2323
const DEFAULT_HOST = '127.0.0.1';
24+
const DEFAULT_TIMEOUT = 1;
2425

25-
private $instance = null;
26+
private $instance = null;
27+
private $requestTimeout = null;
28+
private $connectTimeout = null;
29+
private $host = null;
30+
private $port = null;
31+
private $triedConnect = false;
2632

2733
/**
2834
* @return PeclMemcached
2935
**/
3036
public static function create(
3137
$host = Memcached::DEFAULT_HOST,
32-
$port = Memcached::DEFAULT_PORT
38+
$port = Memcached::DEFAULT_PORT,
39+
$connectTimeout = PeclMemcached::DEFAULT_TIMEOUT
3340
)
3441
{
35-
return new self($host, $port);
42+
return new self($host, $port, $connectTimeout);
3643
}
3744

3845
public function __construct(
3946
$host = Memcached::DEFAULT_HOST,
40-
$port = Memcached::DEFAULT_PORT
47+
$port = Memcached::DEFAULT_PORT,
48+
$connectTimeout = PeclMemcached::DEFAULT_TIMEOUT
4149
)
4250
{
43-
$this->instance = new Memcache();
44-
45-
try {
46-
try {
47-
$this->instance->pconnect($host, $port);
48-
} catch (BaseException $e) {
49-
$this->instance->connect($host, $port);
50-
}
51-
52-
$this->alive = true;
53-
} catch (BaseException $e) {
54-
// bad luck.
55-
}
51+
$this->host = $host;
52+
$this->port = $port;
53+
$this->connectTimeout = $connectTimeout;
5654
}
5755

5856
public function __destruct()
@@ -66,11 +64,20 @@ public function __destruct()
6664
}
6765
}
6866

67+
public function isAlive()
68+
{
69+
$this->ensureTriedToConnect();
70+
71+
return parent::isAlive();
72+
}
73+
6974
/**
7075
* @return PeclMemcached
7176
**/
7277
public function clean()
7378
{
79+
$this->ensureTriedToConnect();
80+
7481
try {
7582
$this->instance->flush();
7683
} catch (BaseException $e) {
@@ -82,6 +89,8 @@ public function clean()
8289

8390
public function increment($key, $value)
8491
{
92+
$this->ensureTriedToConnect();
93+
8594
try {
8695
return $this->instance->increment($key, $value);
8796
} catch (BaseException $e) {
@@ -91,6 +100,8 @@ public function increment($key, $value)
91100

92101
public function decrement($key, $value)
93102
{
103+
$this->ensureTriedToConnect();
104+
94105
try {
95106
return $this->instance->decrement($key, $value);
96107
} catch (BaseException $e) {
@@ -100,6 +111,8 @@ public function decrement($key, $value)
100111

101112
public function getList($indexes)
102113
{
114+
$this->ensureTriedToConnect();
115+
103116
return
104117
($return = $this->get($indexes))
105118
? $return
@@ -108,6 +121,8 @@ public function getList($indexes)
108121

109122
public function get($index)
110123
{
124+
$this->ensureTriedToConnect();
125+
111126
try {
112127
return $this->instance->get($index);
113128
} catch (BaseException $e) {
@@ -124,6 +139,8 @@ public function get($index)
124139

125140
public function delete($index)
126141
{
142+
$this->ensureTriedToConnect();
143+
127144
try {
128145
// second parameter required, wrt new memcached protocol:
129146
// delete key 0 (see process_delete_command in the memcached.c)
@@ -138,6 +155,8 @@ public function delete($index)
138155

139156
public function append($key, $data)
140157
{
158+
$this->ensureTriedToConnect();
159+
141160
try {
142161
return $this->instance->append($key, $data);
143162
} catch (BaseException $e) {
@@ -147,10 +166,58 @@ public function append($key, $data)
147166
Assert::isUnreachable();
148167
}
149168

169+
/**
170+
* @param float $requestTimeout time in seconds
171+
* @return PeclMemcached
172+
*/
173+
public function setTimeout($requestTimeout)
174+
{
175+
$this->ensureTriedToConnect();
176+
$this->requestTimeout = $requestTimeout;
177+
$this->instance->setServerParams($this->host, $this->port, $requestTimeout);
178+
179+
return $this;
180+
}
181+
182+
/**
183+
* @return float
184+
*/
185+
public function getTimeout()
186+
{
187+
return $this->requestTimeout;
188+
}
189+
190+
protected function ensureTriedToConnect()
191+
{
192+
if ($this->triedConnect)
193+
return $this;
194+
195+
$this->triedConnect = true;
196+
$this->instance = new Memcache();
197+
198+
try {
199+
200+
try {
201+
$this->instance->pconnect($this->host, $this->port, $this->connectTimeout);
202+
} catch (BaseException $e) {
203+
$this->instance->connect($this->host, $this->port, $this->connectTimeout);
204+
}
205+
206+
$this->alive = true;
207+
208+
} catch (BaseException $e) {
209+
// bad luck.
210+
}
211+
212+
return $this;
213+
}
214+
150215
protected function store(
151216
$action, $key, $value, $expires = Cache::EXPIRES_MEDIUM
152217
)
153218
{
219+
$this->ensureTriedToConnect();
220+
154221
try {
155222
return
156223
$this->instance->$action(
@@ -167,5 +234,5 @@ protected function store(
167234

168235
Assert::isUnreachable();
169236
}
237+
170238
}
171-
?>

core/Cache/SequentialCache.class.php

Lines changed: 132 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,132 @@
1+
<?php
2+
/****************************************************************************
3+
* Copyright (C) 2012 by Artem Naumenko *
4+
* *
5+
* This program is free software; you can redistribute it and/or modify *
6+
* it under the terms of the GNU Lesser General Public License as *
7+
* published by the Free Software Foundation; either version 3 of the *
8+
* License, or (at your option) any later version. *
9+
* *
10+
****************************************************************************/
11+
12+
final class SequentialCache extends CachePeer
13+
{
14+
/**
15+
* List of all peers, including master
16+
* @var array of CachePeer
17+
*/
18+
private $list = array();
19+
20+
/**
21+
* List of slaves only
22+
* @var array of CachePeer
23+
*/
24+
private $slaves = array();
25+
26+
/**
27+
* @var CachePeer
28+
*/
29+
private $master = null;
30+
31+
/**
32+
* @param CachePeer $master
33+
* @param array $slaves or CachePeer
34+
* @return SequentialCache
35+
*/
36+
public static function create(CachePeer $master, array $slaves = array())
37+
{
38+
return new self($master, $slaves);
39+
}
40+
41+
/**
42+
* @param CachePeer $master
43+
* @param array $slaves or CachePeer
44+
*/
45+
public function __construct(CachePeer $master, array $slaves = array())
46+
{
47+
$this->setMaster($master);
48+
49+
foreach ($slaves as $cache) {
50+
$this->addPeer($cache);
51+
}
52+
}
53+
54+
/**
55+
* @param CachePeer $master
56+
* @return \SequentialCache
57+
*/
58+
public function setMaster(CachePeer $master)
59+
{
60+
$this->master = $master;
61+
$this->list = $this->slaves;
62+
array_unshift($this->list, $this->master);
63+
64+
return $this;
65+
}
66+
67+
/**
68+
* @param CachePeer $master
69+
* @return \SequentialCache
70+
*/
71+
public function addPeer(CachePeer $peer)
72+
{
73+
$this->list[] = $peer;
74+
$this->slaves[] = $peer;
75+
76+
return $this;
77+
}
78+
79+
public function get($key)
80+
{
81+
foreach ($this->list as $val) {
82+
/* @var $val CachePeer */
83+
$result = $val->get($key);
84+
85+
if (
86+
!empty($result)
87+
|| $val->isAlive()
88+
) {
89+
return $result;
90+
}
91+
}
92+
93+
throw new RuntimeException('All peers are dead');
94+
}
95+
96+
public function append($key, $data)
97+
{
98+
return $this->foreachItem(__METHOD__, func_get_args());
99+
}
100+
101+
public function decrement($key, $value)
102+
{
103+
throw new UnsupportedMethodException('decrement is not supported');
104+
}
105+
106+
public function delete($key)
107+
{
108+
return $this->foreachItem(__METHOD__, func_get_args());
109+
}
110+
111+
public function increment($key, $value)
112+
{
113+
throw new UnsupportedMethodException('increment is not supported');
114+
}
115+
116+
protected function store($action, $key, $value, $expires = Cache::EXPIRES_MEDIUM)
117+
{
118+
return $this->foreachItem(__METHOD__, func_get_args());
119+
}
120+
121+
private function foreachItem($method, array $args)
122+
{
123+
$result = true;
124+
125+
foreach ($this->list as $peer) {
126+
/* @var $peer CachePeer */
127+
$result = call_user_func_array(array($peer, $method), $args) && $result;
128+
}
129+
130+
return $result;
131+
}
132+
}

doc/ChangeLog

Lines changed: 10 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,17 @@
1+
2012-04-26 Artem A. Naumenko, Evgeny V. Kokovikhin
2+
3+
* core/Base/Assert.class.php, core/Cache/PeclMemcached.class.php,
4+
main/Monitoring/PinbedPeclMemcached.class.php, test/main/Utils/PinbaTest.class.php,
5+
core/Cache/SequentialCache.class.php,
6+
test/core/SequentialCacheTest.class.php:
7+
Assert::isObject added, lazy ability to PeclMemcached, Pinba's tests tune,
8+
Addd SequentialCache with tests.
9+
110
2012-04-22 Georgiy T. Kutsurua
211

312
* core/OSQL/DBColumn.class.php: Fix DBColumn
413

5-
2012-04-20 Timofey A. Anisimov
14+
2012-04-20 Timofey A. Anisimov
615

716
* test/main/OsqlSelectTest.class.php,
817
core/SQLFullOuterJoin.class.php,

0 commit comments

Comments
 (0)