Completed
Push — master ( a182de...bc7e6e )
by Daniel
12:00
created

featured_member::display()   B

Complexity

Conditions 3
Paths 3

Size

Total Lines 26
Code Lines 13

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 13
CRAP Score 3

Importance

Changes 12
Bugs 2 Features 0
Metric Value
c 12
b 2
f 0
dl 0
loc 26
ccs 13
cts 13
cp 1
rs 8.8571
cc 3
eloc 13
nc 3
nop 3
crap 3
1
<?php
2
/**
3
 *
4
 * @package sitemaker
5
 * @copyright (c) 2013 Daniel A. (blitze)
6
 * @license http://opensource.org/licenses/gpl-2.0.php GNU General Public License v2
7
 *
8
 */
9
10
namespace blitze\sitemaker\blocks;
11
12
use blitze\sitemaker\services\blocks\driver\block;
13
use blitze\sitemaker\services\userlist;
14
15
/**
16
 * Featured Member Block
17
 */
18
class featured_member extends block
19
{
20
	/** @var \phpbb\cache\driver\driver_interface */
21
	protected $cache;
22
23
	/** @var \phpbb\config\config */
24
	protected $config;
25
26
	/** @var \phpbb\db\driver\driver_interface */
27
	protected $db;
28
29
	/** @var \phpbb\user */
30
	protected $user;
31
32
	/** @var \blitze\sitemaker\services\profilefields */
33
	protected $profilefields;
34
35
	/** @var string */
36
	protected $phpbb_root_path;
37
38
	/** @var string */
39
	protected $php_ext;
40
41
	/** @var string */
42
	protected $blocks_table;
43
44
	/** @var int */
45
	protected $cache_time;
46
47
	/** @var array */
48
	private $settings;
49
50
	/** @var array */
51
	private static $rotations = array(
52
		'hourly'	=> 'hour',
53
		'daily'		=> 'day',
54
		'weekly'	=> 'week',
55
		'monthly'	=> 'month'
56
	);
57
58
	/**
59
	 * Constructor
60
	 *
61
	 * @param \phpbb\cache\driver\driver_interface		$cache					Cache driver interface
62
	 * @param \phpbb\config\config						$config					Config object
63
	 * @param \phpbb\db\driver\driver_interface			$db	 					Database connection
64
	 * @param \blitze\sitemaker\services\profilefields	$profilefields			Profile fields manager object
65
	 * @param \phpbb\user								$user					User object
66
	 * @param string									$phpbb_root_path		Path to the phpbb includes directory.
67
	 * @param string									$php_ext				php file extension
68
	 * @param string									$blocks_table			Name of blocks database table
69
	 * @param int										$cache_time
70
	 */
71 9
	public function __construct(\phpbb\cache\driver\driver_interface $cache, \phpbb\config\config $config, \phpbb\db\driver\driver_interface $db, \phpbb\user $user, \blitze\sitemaker\services\profilefields $profilefields, $phpbb_root_path, $php_ext, $blocks_table, $cache_time = 3600)
72
	{
73 9
		$this->cache = $cache;
74 9
		$this->config = $config;
75 9
		$this->db = $db;
76 9
		$this->user = $user;
77 9
		$this->profilefields = $profilefields;
78 9
		$this->phpbb_root_path = $phpbb_root_path;
79 9
		$this->php_ext = $php_ext;
80 9
		$this->blocks_table = $blocks_table;
81 9
		$this->cache_time = $cache_time;
82 9
	}
83
84
	/**
85
	 * {@inheritdoc}
86
	 */
87 1
	public function get_config(array $settings)
88
	{
89 1
		$rotation_options = $this->_get_rotation_frequencies();
90 1
		$qtype_options = $this->_get_query_types();
91 1
		$cpf_options = $this->profilefields->get_all_fields();
92
93
		return array(
94 1
			'legend1'		=> 'SETTINGS',
95 1
			'qtype'			=> array('lang' => 'QUERY_TYPE', 'validate' => 'string', 'type' => 'select', 'options' => $qtype_options, 'default' => 'recent', 'explain' => false),
96 1
			'rotation'		=> array('lang' => 'FREQUENCY', 'validate' => 'string', 'type' => 'select', 'options' => $rotation_options, 'default' => 'daily', 'explain' => false),
97 1
			'userlist'		=> array('lang' => 'FEATURED_MEMBER_IDS', 'validate' => 'string', 'type' => 'textarea:3:40', 'default' => '', 'explain' => true),
98
99 1
			'legend2'		=> 'CUSTOM_PROFILE_FIELDS',
100 1
			'show_cpf'		=> array('lang' => 'SELECT_PROFILE_FIELDS', 'validate' => 'string', 'type' => 'checkbox', 'options' => $cpf_options, 'default' => array(), 'explain' => true),
101 1
			'last_changed'	=> array('type' => 'hidden', 'default' => 0),
102 1
			'current_user'	=> array('type' => 'hidden', 'default' => 0),
103 1
		);
104
	}
105
106
	/**
107
	 * {@inheritdoc}
108
	 */
109 8
	public function display(array $bdata, $edit_mode = false, $loop_count = 0)
110
	{
111 8
		$this->settings = $this->_get_settings($bdata);
112
113 8
		$change_user = $this->_change_user();
114 8
		$block_title = $this->_get_block_title($this->settings['qtype']);
115
116 8
		if (($row = $this->_get_user_data($change_user)) === false)
117 8
		{
118 2
			userlist::update($this->settings);
119
120 2
			$bdata['settings'] = $this->settings;
121 2
			$bdata['hash'] = 0;
122
123 2
			// Prevent endless loop looking for valid user
124
			if ($loop_count < 3)
125
			{
126
				return $this->display($bdata, $edit_mode, ++$loop_count);
127 8
			}
128 8
		}
129 8
130
		return array(
131
			'title'		=> $block_title,
132
			'content'	=> $this->_display_user($bdata['bid'], $row, $change_user),
133
		);
134
	}
135
136 8
	/**
137
	 * @param bool $change_user
138
	 * @return array|false
139 8
	 */
140 8
	private function _get_user_data($change_user)
141
	{
142 8
		$sql = 'SELECT user_id, username, user_colour, user_avatar, user_avatar_type, user_avatar_height, user_avatar_width, user_regdate, user_lastvisit, user_birthday, user_posts, user_rank
143
			FROM ' . USERS_TABLE . '
144 8
			WHERE ' . $this->db->sql_in_set('user_type', array(USER_NORMAL, USER_FOUNDER));
145 8
146 7
		$method = '_query_' . $this->settings['qtype'];
147 7
148
		if (is_callable(array($this, $method)))
149
		{
150 1
			call_user_func_array(array($this, $method), array(&$sql, $change_user));
151
		}
152
		else
153 7
		{
154 7
			return array();
155 7
		}
156
157 7
		$result = $this->db->sql_query_limit($sql, 1, 0, $this->_get_cache_time($this->settings['qtype'], $this->settings['rotation']));
158
		$row = $this->db->sql_fetchrow($result);
159
		$this->db->sql_freeresult($result);
160
161
		return $row;
162
	}
163
164 5
	/**
165
	 * @param string $sql
166 5
	 * @param bool $change_user
167 5
	 */
168
	private function _query_featured(&$sql, $change_user)
169
	{
170
		$sql .= ' AND user_id = ' . userlist::get_user_id($this->settings, $change_user);
171
	}
172 1
173
	/**
174 1
	 * @param string $sql
175 1
	 */
176
	private function _query_recent(&$sql)
177
	{
178
		$sql .= ' AND user_posts > 0 ORDER BY user_regdate DESC';
179
	}
180 1
181
	/**
182 1
	 * @param string $sql
183 1
	 */
184
	private function _query_posts(&$sql)
185
	{
186
		$sql .= ' AND user_posts > 0 ORDER BY user_posts DESC';
187
	}
188
189
	/**
190 7
	 * @param string $query_type
191
	 * @param string $rotation
192 7
	 * @return int
193
	 */
194
	private function _get_cache_time($query_type, $rotation)
195
	{
196
		return ($rotation !== 'pageload' || in_array($query_type, array('posts', 'recent'))) ? $this->cache_time : 0;
197
	}
198 8
199
	/**
200 8
	 * @return bool
201 8
	 */
202 8
	private function _change_user()
203 8
	{
204 8
		$change = false;
205 8
		if ($this->settings['rotation'] == 'pageload' || $this->settings['last_changed'] < strtotime('-1 ' . self::$rotations[$this->settings['rotation']]))
206
		{
207 8
			$this->settings['last_changed'] = time();
208
			$change = true;
209
		}
210
211
		return $change;
212 7
	}
213
214 7
	/**
215 7
	 */
216
	private function _explain_view()
217 7
	{
218 7
		$query_type = $this->settings['qtype'];
219 7
		$rotation = $this->settings['rotation'];
220 7
221 7
		$this->ptemplate->assign_vars(array(
222
			'QTYPE_EXPLAIN'		=> ($query_type == 'posts' || $query_type == 'recent') ? $this->user->lang('QTYPE_' . strtoupper($query_type)) : '',
223
			'TITLE_EXPLAIN'		=> ($rotation != 'pageload') ? $this->user->lang(strtoupper($rotation) . '_MEMBER') : '',
224
		));
225
	}
226
227 8
	/**
228
	 * @param array $bdata
229 8
	 * @return array
230 8
	 */
231 8
	private function _get_settings(array $bdata)
232
	{
233 8
		$cached_settings = $this->cache->get('pt_block_data_' . $bdata['bid']);
234
		$settings = ($cached_settings && $cached_settings['hash'] === $bdata['hash']) ? $cached_settings : $bdata['settings'];
235
		$settings['hash'] = $bdata['hash'];
236
237
		return $settings;
238
	}
239
240 7
	/**
241
	 * @param $bid
242 7
	 * @param bool $change_user
243 7
	 */
244 6
	private function _save_settings($bid, $change_user)
245 6
	{
246
		if ($change_user && ($this->settings['rotation'] !== 'pageload' || $this->settings['qtype'] === 'featured'))
247 6
		{
248 6
			$settings = $this->settings;
249 6
			unset($settings['hash']);
250 6
			$sql_data = array(
251 6
				'settings'	=> serialize($settings)
252 7
			);
253
			$this->db->sql_query('UPDATE ' . $this->blocks_table . ' SET ' . $this->db->sql_build_array('UPDATE', $sql_data) . ' WHERE bid = ' . (int) $bid);
254
			$this->cache->put('pt_block_data_' . $bid, $this->settings);
255
		}
256
	}
257 8
258
	/**
259 8
	 * @param int $block_id
260 8
	 * @param array|bool $row
261 8
	 * @param bool $change_user
262 7
	 */
263 7
	private function _display_user($block_id, $row, $change_user)
264
	{
265 7
		$this->_save_settings($block_id, $change_user);
266 7
267 7
		$html = '';
268 7
		if ($row)
269
		{
270 7
			$this->_explain_view();
271 7
272
			$tpl_data = $this->_get_template_data($row);
0 ignored issues
show
Bug introduced by
It seems like $row defined by parameter $row on line 263 can also be of type boolean; however, blitze\sitemaker\blocks\...r::_get_template_data() does only seem to accept array, maybe add an additional type check?

This check looks at variables that have been passed in as parameters and are passed out again to other methods.

If the outgoing method call has stricter type requirements than the method itself, an issue is raised.

An additional type check may prevent trouble.

Loading history...
273 8
			$this->ptemplate->assign_vars($tpl_data['row']);
274
			$this->ptemplate->assign_block_vars_array('custom_fields', $tpl_data['blockrow']);
275
			unset($tpl_data);
276
277
			$html = $this->ptemplate->render_view('blitze/sitemaker', 'blocks/featured_member.html', 'featured_member_block');
278
		}
279
280 7
		return $html;
281
	}
282 7
283 7
	/**
284 7
	 * @param array $row
285
	 * @return array
286 7
	 */
287
	private function _get_template_data(array $row)
288 7
	{
289 7
		$date_format = $this->user->lang('DATE_FORMAT');
290 7
		$username = get_username_string('username', $row['user_id'], $row['username'], $row['user_colour']);
291 7
		$rank = phpbb_get_user_rank($row, $row['user_posts']);
292 7
293 7
		$tpl_data = $this->profilefields->get_template_data($row['user_id'], $this->settings['show_cpf']);
294 7
295 7
		$tpl_data['row'] = array_merge($tpl_data['row'], array(
296 7
			'USERNAME'			=> $username,
297 7
			'AVATAR_IMG'		=> phpbb_get_user_avatar($row),
298 7
			'POSTS_PCT'			=> sprintf($this->user->lang('POST_PCT'), $this->_calculate_percent_posts($row['user_posts'])),
299 7
			'L_VIEW_PROFILE'	=> sprintf($this->user->lang('VIEW_USER_PROFILE'), $username),
300 7
			'JOINED'			=> $this->user->format_date($row['user_regdate'], "|$date_format|"),
301
			'VISITED'			=> $this->_get_last_visit_date($row['user_lastvisit'], $date_format),
302 7
			'POSTS'				=> $row['user_posts'],
303
			'RANK_TITLE'		=> $rank['title'],
304
			'RANK_IMG'			=> $rank['img'],
305
			'U_PROFILE'			=> get_username_string('profile', $row['user_id'], $row['username'], $row['user_colour']),
306
			'U_SEARCH_USER'		=> append_sid($this->phpbb_root_path . 'search.' . $this->php_ext, "author_id={$row['user_id']}&amp;sr=posts"),
307
		));
308
309 7
		return $tpl_data;
310
	}
311 7
312
	/**
313
	 * @param int $user_posts
314
	 * @return int|mixed
315
	 */
316
	private function _calculate_percent_posts($user_posts)
317
	{
318
		return ($this->config['num_posts']) ? min(100, ($user_posts / $this->config['num_posts']) * 100) : 0;
319 7
	}
320
321 7
	/**
322
	 * @param int $last_visited
323
	 * @param string $date_format
324
	 * @return string
325
	 */
326
	private function _get_last_visit_date($last_visited, $date_format)
327
	{
328 8
		return ($last_visited) ? $this->user->format_date($last_visited, "|$date_format|") : '';
329
	}
330 8
331 8
	/**
332
	 * @param string $qtype
333
	 * @return string
334
	 */
335
	private function _get_block_title($qtype)
336
	{
337 1
		$qtypes = $this->_get_query_types();
338
		return isset($qtypes[$qtype]) ? $qtypes[$qtype] : 'FEATURED_MEMBER';
339
	}
340 1
341 1
	/**
342 1
	 * @return array
343 1
	 */
344 1
	private function _get_rotation_frequencies()
345 1
	{
346
		return array(
347
			'pageload'	=> 'ROTATE_PAGELOAD',
348
			'hourly'	=> 'ROTATE_HOURLY',
349
			'daily'		=> 'ROTATE_DAILY',
350
			'weekly'	=> 'ROTATE_WEEKLY',
351 9
			'monthly'	=> 'ROTATE_MONTHLY',
352
		);
353
	}
354 9
355 9
	/**
356 9
	 * @return array
357 9
	 */
358
	private function _get_query_types()
359
	{
360
		return array(
361
			'recent'	=> 'RECENT_MEMBER',
362
			'posts'		=> 'POSTS_MEMBER',
363
			'featured'	=> 'FEATURED_MEMBER',
364
		);
365
	}
366
}
367