Passed
Pull Request — release-2.1 (#6262)
by Jeremy
04:04
created

memcached_cache::addServers()   A

Complexity

Conditions 6
Paths 7

Size

Total Lines 25
Code Lines 11

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 6
eloc 11
nc 7
nop 0
dl 0
loc 25
rs 9.2222
c 0
b 0
f 0
1
<?php
2
3
/**
4
 * Simple Machines Forum (SMF)
5
 *
6
 * @package SMF
7
 * @author Simple Machines https://www.simplemachines.org
8
 * @copyright 2020 Simple Machines and individual contributors
9
 * @license https://www.simplemachines.org/about/smf/license.php BSD
10
 *
11
 * @version 2.1 RC3
12
 */
13
14
if (!defined('SMF'))
15
	die('Hacking attempt...');
16
17
/**
18
 * Our Cache API class
19
 *
20
 * @package cacheAPI
21
 */
22
class memcached_cache extends cache_api
23
{
24
	/** @var Memcached The memcache instance. */
25
	private $memcached = null;
26
27
	/** @var string[] */
28
	private $servers;
29
30
	/**
31
	 * {@inheritDoc}
32
	 */
33
	public function __construct()
34
	{
35
		global $cache_memcached;
36
37
		$this->servers = array_map(
38
			function($server)
39
			{
40
				if (strpos($server, '/') !== false)
41
					return array($server, 0);
42
				else
43
					return array($server, isset($server[1]) ? $server[1] : 11211);
44
			},
45
			explode(',', $cache_memcached)
46
		);
47
48
		parent::__construct();
49
	}
50
51
	/**
52
	 * {@inheritDoc}
53
	 */
54
	public function isSupported($test = false)
55
	{
56
		global $cache_memcached;
57
58
		$supported = class_exists('Memcached');
59
60
		if ($test)
61
			return $supported;
62
		return parent::isSupported() && $supported && !empty($cache_memcached);
63
	}
64
65
	/**
66
	 * {@inheritDoc}
67
	 */
68
	public function connect()
69
	{
70
		$this->memcached = new Memcached;
71
72
		return $this->addServers();
73
	}
74
75
	/**
76
	 * Add memcached servers.
77
	 *
78
	 * Don't add servers if they already exist. Ideal for persistent connections.
79
	 *
80
	 * @return bool True if there are servers in the daemon, false if not.
81
	 */
82
	protected function addServers()
83
	{
84
		// memcached does not remove servers from the list upon completing the
85
		// script under modes like FastCGI. So check to see if servers exist or not.
86
		$currentServers = $this->memcached->getServerList();
87
		$retVal = !empty($currentServers);
88
		foreach ($this->servers as $server)
89
		{
90
			// Figure out if we have this server or not
91
			$foundServer = false;
92
			foreach ($currentServers as $currentServer)
93
			{
94
				if ($server[0] == $currentServer['host'] && $server[1] == $currentServer['port'])
95
				{
96
					$foundServer = true;
97
					break;
98
				}
99
			}
100
101
			// Found it?
102
			if (empty($foundServer))
103
				$retVal |= $this->memcached->addServer($server[0], $server[1]);
104
		}
105
106
		return $retVal;
107
	}
108
109
	/**
110
	 * {@inheritDoc}
111
	 */
112
	public function getData($key, $ttl = null)
113
	{
114
		$key = $this->prefix . strtr($key, ':/', '-_');
115
116
		$value = $this->memcached->get($key);
117
118
		// $value should return either data or false (from failure, key not found or empty array).
119
		if ($value === false)
120
			return null;
121
		return $value;
122
	}
123
124
	/**
125
	 * {@inheritDoc}
126
	 */
127
	public function putData($key, $value, $ttl = null)
128
	{
129
		$key = $this->prefix . strtr($key, ':/', '-_');
130
131
		return $this->memcached->set($key, $value, $ttl !== null ? $ttl : $this->ttl);
132
	}
133
134
	/**
135
	 * {@inheritDoc}
136
	 */
137
	public function cleanCache($type = '')
138
	{
139
		$this->invalidateCache();
140
141
		// Memcached accepts a delay parameter, always use 0 (instant).
142
		return $this->memcached->flush(0);
143
	}
144
145
	/**
146
	 * {@inheritDoc}
147
	 */
148
	public function quit()
149
	{
150
		return $this->memcached->quit();
151
	}
152
153
	/**
154
	 * {@inheritDoc}
155
	 */
156
	public function cacheSettings(array &$config_vars)
157
	{
158
		global $context, $txt;
159
160
		$config_vars[] = $txt['cache_memcache_settings'];
161
		$config_vars[] = array('cache_memcached', $txt['cache_memcache_servers'], 'file', 'text', 0, 'cache_memcached', 'postinput' => '<br><div class="smalltext"><em>' . $txt['cache_memcache_servers_subtext'] . '</em></div>');
162
163
		if (!isset($context['settings_post_javascript']))
164
			$context['settings_post_javascript'] = '';
165
166
		$context['settings_post_javascript'] .= '
167
			$("#cache_accelerator").change(function (e) {
168
				var cache_type = e.currentTarget.value;
169
				$("#cache_memcached").prop("disabled", cache_type != "memcached");
170
			});';
171
	}
172
173
	/**
174
	 * {@inheritDoc}
175
	 */
176
	public function getVersion()
177
	{
178
		return current($this->memcached->getVersion());
179
	}
180
}
181
182
?>