Skip to content

Commit eccc791

Browse files
authored
Merge pull request #566 from Geolim4/final
Fixed #563
2 parents 76bb1fc + 700dcf0 commit eccc791

File tree

7 files changed

+172
-37
lines changed

7 files changed

+172
-37
lines changed

docs/OPTIONS.md

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,9 @@
11
PhpFastCache has some options that you may want to know before using them, here's the list:
22

33
### File-based drivers options *
4+
* **path** See the "**Host/Authenticating options**" section
45
* **default_chmod** _| int>octal (default: 0777)_ `[>=V4]` This option will define the chmod used to write driver cache files.
56
* **securityKey** _| string (default: 'auto')_ `[>=V4]` A security key that define the subdirectory name. 'auto' value will be the HTTP_HOST value.
6-
* **path** _| string (default: Tmp directory)_ `[>=V4]` The absolute path where the written cache files belong to.
77
* **htaccess** _| bool (default: true)_ `[>=V4]` Option designed to (dis)allow the auto-generation of .htaccess.
88
* **autoTmpFallback** _| bool (default: false)_ `[>=V6]`Option designed to automatically attempt to fallback to temporary directory if the cache fails to write on the specified directory
99
* **secureFileManipulation** _| bool (default: false)_ `[>=V6]` This option enforces a strict I/O manipulation policy by adding more integrity checks. This option may slow down the write operations, therefore you must use it with caution. In case of failure an **phpFastCacheIOException** exception will be thrown. Currently only supported by _Files_ driver.
@@ -22,11 +22,13 @@ PhpFastCache has some options that you may want to know before using them, here'
2222
* **cacheSlamsTimeout** _| int (default: 15)_ `[>=V6]` This option defines the cache slams timeout in seconds
2323

2424
### Host/Authenticating options *
25-
* **host** _| string (default: not set)_ The host
25+
* **host** _| string (default: not set)_ The hostname
26+
* **path** _| string (default: not set)_ `[>=V4], [>=V6.1]` The absolute path where the written cache files belong to (system temp directory by default). **As of the V6.1** this option is also used to define (P)redis and Memcache(d) UNIX socket
2627
* **port** _| int (default: not set)_ The port
2728
* **username** _| string (default: not set)_ The username
2829
* **password** _| string (default: not set)_ The password
2930
* **timeout** _| int (default: not set)_ The timeout (in seconds)
31+
* **servers** _| array (default: not set)_ Array of servers. Exclusive to Memcache(d)
3032

3133
These options differs depending the driver that you are using, see **/Examples** folder for more information about these options.
3234

src/phpFastCache/CacheManager.php

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -460,8 +460,8 @@ protected static function validateConfig(array $config)
460460
break;
461461
case 'securityKey':
462462
case 'path':
463-
if (!is_string($configValue)) {
464-
throw new phpFastCacheInvalidConfigurationException("{$configName} must be a string");
463+
if (!is_string($configValue) && (!is_bool($configValue) || $configValue)) {
464+
throw new phpFastCacheInvalidConfigurationException("{$configName} must be a string or a false boolean");
465465
}
466466
break;
467467
case 'default_chmod':

src/phpFastCache/Drivers/Memcache/Driver.php

Lines changed: 26 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -78,12 +78,12 @@ protected function driverWrite(CacheItemInterface $item)
7878
* Check for Cross-Driver type confusion
7979
*/
8080
if ($item instanceof Item) {
81-
$ttl = $item->getExpirationDate()->getTimestamp() - time();
81+
$ttl = $item->getTtl();
8282

8383
// Memcache will only allow a expiration timer less than 2592000 seconds,
8484
// otherwise, it will assume you're giving it a UNIX timestamp.
85-
if ($ttl > 2592000) {
86-
$ttl = time() + $ttl;
85+
if ($ttl >= 2592000) {
86+
$ttl = $item->getExpirationDate()->getTimestamp();
8787
}
8888

8989
return $this->instance->set($item->getKey(), $this->driverPreWrap($item), $this->memcacheFlags, $ttl);
@@ -142,26 +142,43 @@ protected function driverConnect()
142142
if (count($servers) < 1) {
143143
$servers = [
144144
[
145-
'host' => '127.0.0.1',
146-
'port' => 11211,
147-
'sasl_user' => false,
148-
'sasl_password' => false,
145+
'host' => !empty($this->config[ 'host' ]) ? $this->config[ 'host' ] : '127.0.0.1',
146+
'path' => !empty($this->config[ 'path' ]) ? $this->config[ 'path' ] : false,
147+
'port' => !empty($this->config[ 'port' ]) ? $this->config[ 'port' ] : 11211,
148+
'sasl_user' => !empty($this->config[ 'sasl_user' ]) ? $this->config[ 'sasl_user' ] : false,
149+
'sasl_password' =>!empty($this->config[ 'sasl_password' ]) ? $this->config[ 'sasl_password' ]: false,
149150
],
150151
];
151152
}
152153

153154
foreach ($servers as $server) {
154155
try {
155-
if (!$this->instance->addServer($server[ 'host' ], $server[ 'port' ])) {
156+
/**
157+
* If path is provided we consider it as an UNIX Socket
158+
*/
159+
if(!empty($server[ 'path' ]) && !$this->instance->addServer($server[ 'path' ], 0)){
160+
$this->fallback = true;
161+
}else if (!empty($server[ 'host' ]) && !$this->instance->addServer($server[ 'host' ], $server[ 'port' ])) {
156162
$this->fallback = true;
157163
}
164+
158165
if (!empty($server[ 'sasl_user' ]) && !empty($server[ 'sasl_password' ])) {
159-
$this->instance->setSaslAuthData($server[ 'sasl_user' ], $server[ 'sasl_password' ]);
166+
throw new phpFastCacheDriverException('Unlike Memcached, Memcache does not support SASL authentication');
160167
}
161168
} catch (\Exception $e) {
162169
$this->fallback = true;
163170
}
171+
172+
/**
173+
* Since Memcached does not throw
174+
* any error if not connected ...
175+
*/
176+
if(!$this->instance->getServerStatus(!empty($server[ 'path' ]) ? $server[ 'path' ] : $server[ 'host' ], !empty($server[ 'port' ]) ? $server[ 'port' ] : 0)){
177+
throw new phpFastCacheDriverException('Memcache seems to not be connected');
178+
}
164179
}
180+
181+
return true;
165182
}
166183

167184
/********************

src/phpFastCache/Drivers/Memcached/Driver.php

Lines changed: 26 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -69,12 +69,12 @@ protected function driverWrite(CacheItemInterface $item)
6969
* Check for Cross-Driver type confusion
7070
*/
7171
if ($item instanceof Item) {
72-
$ttl = $item->getExpirationDate()->getTimestamp() - time();
72+
$ttl = $item->getTtl();
7373

7474
// Memcache will only allow a expiration timer less than 2592000 seconds,
7575
// otherwise, it will assume you're giving it a UNIX timestamp.
76-
if ($ttl > 2592000) {
77-
$ttl = time() + $ttl;
76+
if ($ttl >= 2592000) {
77+
$ttl = $item->getExpirationDate()->getTimestamp();
7878
}
7979

8080
return $this->instance->set($item->getKey(), $this->driverPreWrap($item), $ttl);
@@ -136,26 +136,44 @@ protected function driverConnect()
136136
if (count($servers) < 1) {
137137
$servers = [
138138
[
139-
'host' => '127.0.0.1',
140-
'port' => 11211,
141-
'sasl_user' => false,
142-
'sasl_password' => false,
139+
'host' => !empty($this->config[ 'host' ]) ? $this->config[ 'host' ] : '127.0.0.1',
140+
'path' => !empty($this->config[ 'path' ]) ? $this->config[ 'path' ] : false,
141+
'port' => !empty($this->config[ 'port' ]) ? $this->config[ 'port' ] : 11211,
142+
'sasl_user' => !empty($this->config[ 'sasl_user' ]) ? $this->config[ 'sasl_user' ] : false,
143+
'sasl_password' =>!empty($this->config[ 'sasl_password' ]) ? $this->config[ 'sasl_password' ]: false,
143144
],
144145
];
145146
}
146147

147148
foreach ($servers as $server) {
148149
try {
149-
if (!$this->instance->addServer($server[ 'host' ], $server[ 'port' ])) {
150+
/**
151+
* If path is provided we consider it as an UNIX Socket
152+
*/
153+
if(!empty($server[ 'path' ]) && !$this->instance->addServer($server[ 'path' ], 0)){
154+
$this->fallback = true;
155+
}else if (!empty($server[ 'host' ]) && !$this->instance->addServer($server[ 'host' ], $server[ 'port' ])) {
150156
$this->fallback = true;
151157
}
158+
152159
if (!empty($server[ 'sasl_user' ]) && !empty($server[ 'sasl_password' ])) {
153160
$this->instance->setSaslAuthData($server[ 'sasl_user' ], $server[ 'sasl_password' ]);
154161
}
162+
155163
} catch (\Exception $e) {
156164
$this->fallback = true;
157165
}
158166
}
167+
168+
/**
169+
* Since Memcached does not throw
170+
* any error if not connected ...
171+
*/
172+
$version = $this->instance->getVersion();
173+
if(!$version || $this->instance->getResultCode() !== MemcachedSoftware::RES_SUCCESS){
174+
throw new phpFastCacheDriverException('Memcached seems to not be connected');
175+
}
176+
return true;
159177
}
160178

161179
/********************

src/phpFastCache/Drivers/Predis/Driver.php

Lines changed: 19 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -133,19 +133,34 @@ protected function driverClear()
133133
*/
134134
protected function driverConnect()
135135
{
136-
$config = isset($this->config[ 'predis' ]) ? $this->config[ 'predis' ] : [];
136+
/** Backward compatibility */
137+
$config = isset($this->config[ 'predis' ]) ? $this->config[ 'predis' ] : $this->config;
138+
$path = isset($config[ 'path' ]) ? (string) $config[ 'path' ] : false;
137139

138-
$this->instance = new PredisClient(array_merge([
140+
$defaultConfig = [
139141
'host' => '127.0.0.1',
140142
'port' => 6379,
141143
'password' => null,
142144
'database' => null,
143-
], $config));
145+
];
146+
$config = array_merge($defaultConfig, $config);
147+
148+
/**
149+
* If path is provided we consider it as an UNIX Socket
150+
*/
151+
if($path){
152+
$this->instance = new PredisClient([
153+
'scheme' => 'unix',
154+
'path' => $path
155+
]);
156+
}else{
157+
$this->instance = new PredisClient($config);
158+
}
144159

145160
try {
146161
$this->instance->connect();
147162
} catch (PredisConnectionException $e) {
148-
throw new phpFastCacheDriverException('Failed to connect to predis server', 0, $e);
163+
throw new phpFastCacheDriverException('Failed to connect to predis server. Check the Predis documentation: https://github.com/nrk/predis/tree/v1.1#how-to-install-and-use-predis', 0, $e);
149164
}
150165

151166
return true;

src/phpFastCache/Drivers/Redis/Driver.php

Lines changed: 21 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -134,24 +134,33 @@ protected function driverConnect()
134134
} else {
135135
$this->instance = $this->instance ?: new RedisClient();
136136

137-
$host = isset($this->config[ 'host' ]) ? $this->config[ 'host' ] : '127.0.0.1';
138-
$port = isset($this->config[ 'port' ]) ? (int)$this->config[ 'port' ] : '6379';
139-
$password = isset($this->config[ 'password' ]) ? $this->config[ 'password' ] : '';
140-
$database = isset($this->config[ 'database' ]) ? $this->config[ 'database' ] : '';
141-
$timeout = isset($this->config[ 'timeout' ]) ? $this->config[ 'timeout' ] : '';
137+
$host = isset($this->config[ 'host' ]) ? (string) $this->config[ 'host' ] : '127.0.0.1';
138+
$path = isset($this->config[ 'path' ]) ? (string) $this->config[ 'path' ] : false;
139+
$port = isset($this->config[ 'port' ]) ? (int) $this->config[ 'port' ] : 6379;
140+
$password = isset($this->config[ 'password' ]) ? (string) $this->config[ 'password' ] : '';
141+
$database = isset($this->config[ 'database' ]) ? $this->config[ 'database' ] : false;
142+
$timeout = isset($this->config[ 'timeout' ]) ? $this->config[ 'timeout' ] : '';
142143

143-
if (!$this->instance->connect($host, (int)$port, (int)$timeout)) {
144+
/**
145+
* If path is provided we consider it as an UNIX Socket
146+
*/
147+
if($path){
148+
$isConnected = $this->instance->connect($path);
149+
}else{
150+
$isConnected = $this->instance->connect($host, (int)$port, (int)$timeout);
151+
}
152+
153+
if (!$isConnected && $path) {
144154
return false;
145-
} else {
155+
} else if(!$path) {
146156
if ($password && !$this->instance->auth($password)) {
147157
return false;
148158
}
149-
if ($database) {
150-
$this->instance->select((int)$database);
151-
}
152-
153-
return true;
154159
}
160+
if ($database !== false) {
161+
$this->instance->select((int)$database);
162+
}
163+
return true;
155164
}
156165
}
157166

Lines changed: 74 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,74 @@
1+
<?php
2+
3+
/**
4+
* @author Khoa Bui (khoaofgod) <[email protected]> http://www.phpfastcache.com
5+
* @author Georges.L (Geolim4) <[email protected]>
6+
*/
7+
8+
use phpFastCache\CacheManager;
9+
use phpFastCache\Helper\TestHelper;
10+
11+
chdir(__DIR__);
12+
require_once __DIR__ . '/../vendor/autoload.php';
13+
$testHelper = new TestHelper('Memcached altyernative configuration syntax');
14+
15+
$cacheInstanceDefSyntax = CacheManager::getInstance('Memcached', []);
16+
$cacheInstanceOldSyntax = CacheManager::getInstance('Memcached', [
17+
'servers' => [
18+
[
19+
'host' => '127.0.0.1',
20+
'path' => false,
21+
'port' => 11211,
22+
]
23+
]
24+
]);
25+
$cacheInstanceNewSyntax = CacheManager::getInstance('Memcached', [
26+
'host' => '127.0.0.1',
27+
'path' => false,
28+
'port' => 11211,
29+
]);
30+
$cacheKey = 'cacheKey';
31+
$RandomCacheValue = str_shuffle(uniqid('pfc', true));
32+
33+
$cacheItem = $cacheInstanceDefSyntax->getItem($cacheKey);
34+
$cacheItem->set($RandomCacheValue)->expiresAfter(600);
35+
$cacheInstanceDefSyntax->save($cacheItem);
36+
unset($cacheItem);
37+
$cacheInstanceDefSyntax->detachAllItems();
38+
39+
40+
$cacheItem = $cacheInstanceOldSyntax->getItem($cacheKey);
41+
$cacheItem->set($RandomCacheValue)->expiresAfter(600);
42+
$cacheInstanceOldSyntax->save($cacheItem);
43+
unset($cacheItem);
44+
$cacheInstanceOldSyntax->detachAllItems();
45+
46+
$cacheItem = $cacheInstanceNewSyntax->getItem($cacheKey);
47+
$cacheItem->set($RandomCacheValue)->expiresAfter(600);
48+
$cacheInstanceNewSyntax->save($cacheItem);
49+
unset($cacheItem);
50+
$cacheInstanceNewSyntax->detachAllItems();
51+
52+
53+
if($cacheInstanceDefSyntax->getItem($cacheKey)->isHit()){
54+
$testHelper->printPassText('The default Memcached syntax is working well');
55+
}else{
56+
$testHelper->printFailText('The default Memcached syntax is not working');
57+
}
58+
59+
if($cacheInstanceOldSyntax->getItem($cacheKey)->isHit()){
60+
$testHelper->printPassText('The old Memcached syntax is working well');
61+
}else{
62+
$testHelper->printFailText('The old Memcached syntax is not working');
63+
}
64+
65+
if($cacheInstanceNewSyntax->getItem($cacheKey)->isHit()){
66+
$testHelper->printPassText('The new Memcached syntax is working well');
67+
}else{
68+
$testHelper->printFailText('The new Memcached syntax is not working');
69+
}
70+
71+
$cacheInstanceDefSyntax->clear();
72+
$cacheInstanceOldSyntax->clear();
73+
$cacheInstanceNewSyntax->clear();
74+
$testHelper->terminateTest();

0 commit comments

Comments
 (0)