UsersList.php 6.52 KB
Newer Older
Scott committed
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18
<?php
/*
	Question2Answer by Gideon Greenspan and contributors
	http://www.question2answer.org/

	This program is free software; you can redistribute it and/or
	modify it under the terms of the GNU General Public License
	as published by the Free Software Foundation; either version 2
	of the License, or (at your option) any later version.

	This program is distributed in the hope that it will be useful,
	but WITHOUT ANY WARRANTY; without even the implied warranty of
	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
	GNU General Public License for more details.

	More about this license: http://www.question2answer.org/license.php
*/

19
namespace Q2A\Controllers\User;
Scott committed
20

21
use Q2A\Auth\NoPermissionException;
22 23
use Q2A\Controllers\BaseController;
use Q2A\Database\DbConnection;
24
use Q2A\Middleware\Auth\InternalUsersOnly;
25
use Q2A\Middleware\Auth\MinimumUserLevel;
26

27
class UsersList extends BaseController
Scott committed
28
{
29
	public function __construct(DbConnection $db)
30
	{
31 32 33 34 35
		require_once QA_INCLUDE_DIR . 'db/users.php';
		require_once QA_INCLUDE_DIR . 'db/selects.php';
		require_once QA_INCLUDE_DIR . 'app/users.php';
		require_once QA_INCLUDE_DIR . 'app/format.php';

36
		parent::__construct($db);
37 38

		$this->addMiddleware(new InternalUsersOnly(), array('newest', 'special', 'blocked'));
39
		$this->addMiddleware(new MinimumUserLevel(QA_USER_LEVEL_MODERATOR), array('blocked'));
40 41
	}

42 43 44 45
	/**
	 * Display top users page (ordered by points)
	 * @return array $qa_content
	 */
Scott committed
46 47
	public function top()
	{
48
		// callables to fetch user data
49
		$fetchUsers = function ($start, $pageSize) {
50 51 52 53 54
			return array(
				qa_opt('cache_userpointscount'),
				qa_db_select_with_pending(qa_db_top_users_selectspec($start, $pageSize))
			);
		};
55
		$userScore = function ($user) {
56 57
			return qa_html(qa_format_number($user['points'], 0, true));
		};
Scott committed
58

59
		$qa_content = $this->rankedUsersContent($fetchUsers, $userScore);
Scott committed
60

61 62 63
		$qa_content['title'] = empty($qa_content['ranking']['items'])
			? qa_lang_html('main/no_active_users')
			: qa_lang_html('main/highest_users');
Scott committed
64

65
		$qa_content['ranking']['sort'] = 'points';
Scott committed
66 67 68 69

		return $qa_content;
	}

70 71
	/**
	 * Display newest users page
72
	 *
73
	 * @return array $qa_content
74
	 * @throws NoPermissionException
75
	 */
Scott committed
76 77
	public function newest()
	{
78
		// check we have permission to view this page (moderator or above)
Scott committed
79
		if (qa_user_permit_error('permit_view_new_users_page')) {
80
			throw new NoPermissionException();
Scott committed
81 82
		}

83
		// callables to fetch user data
84
		$fetchUsers = function ($start, $pageSize) {
85 86 87 88 89
			return array(
				qa_opt('cache_userpointscount'),
				qa_db_select_with_pending(qa_db_newest_users_selectspec($start, $pageSize))
			);
		};
90
		$userDate = function ($user) {
91 92 93
			$when = qa_when_to_html($user['created'], 7);
			return $when['data'];
		};
Scott committed
94

95
		$qa_content = $this->rankedUsersContent($fetchUsers, $userDate);
Scott committed
96

97 98 99
		$qa_content['title'] = empty($qa_content['ranking']['items'])
			? qa_lang_html('main/no_active_users')
			: qa_lang_html('main/newest_users');
Scott committed
100

101
		$qa_content['ranking']['sort'] = 'date';
Scott committed
102 103 104 105

		return $qa_content;
	}

106 107
	/**
	 * Display special users page (admins, moderators, etc)
108
	 *
109
	 * @return array $qa_content
110
	 * @throws NoPermissionException
111
	 */
Scott committed
112 113
	public function special()
	{
114
		// check we have permission to view this page (moderator or above)
Scott committed
115
		if (qa_user_permit_error('permit_view_special_users_page')) {
116
			throw new NoPermissionException();
Scott committed
117 118
		}

119
		// callables to fetch user data
120
		$fetchUsers = function ($start, $pageSize) {
121 122 123 124
			// here we fetch *all* users to get the total instead of a separate query; there are unlikely to be many special users
			$users = qa_db_select_with_pending(qa_db_users_from_level_selectspec(QA_USER_LEVEL_EXPERT));
			return array(count($users), $users);
		};
125
		$userLevel = function ($user) {
126 127
			return qa_html(qa_user_level_string($user['level']));
		};
Scott committed
128

129
		$qa_content = $this->rankedUsersContent($fetchUsers, $userLevel);
Scott committed
130 131 132

		$qa_content['title'] = qa_lang_html('users/special_users');

133
		$qa_content['ranking']['sort'] = 'level';
Scott committed
134 135 136 137

		return $qa_content;
	}

138 139 140 141
	/**
	 * Display blocked users page
	 * @return array $qa_content
	 */
Scott committed
142 143
	public function blocked()
	{
144
		// callables to fetch user data
145
		$fetchUsers = function ($start, $pageSize) {
146 147 148 149 150 151 152
			list($totalUsers, $users) = qa_db_select_with_pending(
				qa_db_selectspec_count(qa_db_users_with_flag_selectspec(QA_USER_FLAGS_USER_BLOCKED)),
				qa_db_users_with_flag_selectspec(QA_USER_FLAGS_USER_BLOCKED, $start, $pageSize)
			);

			return array($totalUsers['count'], $users);
		};
153
		$userLevel = function ($user) {
154 155 156 157 158 159 160 161 162 163 164 165 166
			return qa_html(qa_user_level_string($user['level']));
		};

		$qa_content = $this->rankedUsersContent($fetchUsers, $userLevel);

		$qa_content['title'] = empty($qa_content['ranking']['items'])
			? qa_lang_html('users/no_blocked_users')
			: qa_lang_html('users/blocked_users');

		$qa_content['ranking']['sort'] = 'level';

		return $qa_content;
	}
Scott committed
167

168 169 170 171 172 173 174 175 176
	/**
	 * Fetch $qa_content array for a set of ranked users.
	 * @param  callable $fnUsersAndCount Function that returns the list of users for a page and the user total.
	 * @param  callable $fnUserScore Function that returns the "score" (points, date, etc) that will be displayed.
	 * @return array $qa_content
	 */
	private function rankedUsersContent($fnUsersAndCount, $fnUserScore)
	{
		// get the users to display on this page
Scott committed
177

178 179 180
		$request = qa_request();
		$start = qa_get_start();
		$pageSize = qa_opt('page_size_users');
Scott committed
181

182
		list($totalUsers, $users) = $fnUsersAndCount($start, $pageSize);
Scott committed
183

184 185
		// get userids and handles of retrieved users
		$usersHtml = qa_userids_handles_html($users);
Scott committed
186

187
		// prepare content for theme
Scott committed
188

189
		$content = qa_content_prepare();
Scott committed
190

191
		$content['ranking'] = array(
Scott committed
192
			'items' => array(),
193
			'rows' => ceil($pageSize / qa_opt('columns_users')),
Scott committed
194
			'type' => 'users',
195
			// 'sort' is handled by calling code
Scott committed
196 197 198
		);

		foreach ($users as $user) {
199 200 201
			if (QA_FINAL_EXTERNAL_USERS) {
				$avatarHtml = qa_get_external_avatar_html($user['userid'], qa_opt('avatar_users_size'), true);
			} else {
202 203 204 205 206 207 208 209 210 211
				$avatarHtml = qa_get_user_avatar_html(
					$user['flags'],
					$user['email'],
					$user['handle'],
					$user['avatarblobid'],
					$user['avatarwidth'],
					$user['avatarheight'],
					qa_opt('avatar_users_size'),
					true
				);
212 213 214 215 216 217
			}

			$content['ranking']['items'][] = array(
				'avatar' => $avatarHtml,
				'label' => $usersHtml[$user['userid']],
				'score' => $fnUserScore($user),
Scott committed
218 219 220 221
				'raw' => $user,
			);
		}

222
		$content['page_links'] = qa_html_page_links($request, $start, $pageSize, $totalUsers, qa_opt('pages_prev_next'));
Scott committed
223

224
		$content['canonical'] = qa_get_canonical();
Scott committed
225

226
		$content['navigation']['sub'] = qa_users_sub_navigation();
Scott committed
227

228
		return $content;
Scott committed
229 230
	}
}