Code Coverage
 
Lines
Functions and Methods
Classes and Traits
Total
79.38% covered (warning)
79.38%
77 / 97
83.33% covered (warning)
83.33%
5 / 6
CRAP
0.00% covered (danger)
0.00%
0 / 1
helper
79.38% covered (warning)
79.38%
77 / 97
83.33% covered (warning)
83.33%
5 / 6
50.66
0.00% covered (danger)
0.00%
0 / 1
 __construct
100.00% covered (success)
100.00%
18 / 18
100.00% covered (success)
100.00%
1 / 1
1
 get_name
100.00% covered (success)
100.00%
1 / 1
100.00% covered (success)
100.00%
1 / 1
2
 get_name_string
100.00% covered (success)
100.00%
37 / 37
100.00% covered (success)
100.00%
1 / 1
22
 get_rank
100.00% covered (success)
100.00%
20 / 20
100.00% covered (success)
100.00%
1 / 1
5
 get_avatar
100.00% covered (success)
100.00%
1 / 1
100.00% covered (success)
100.00%
1 / 1
1
 display_legend
0.00% covered (danger)
0.00%
0 / 20
0.00% covered (danger)
0.00%
0 / 1
56
1<?php
2/**
3 *
4 * This file is part of the phpBB Forum Software package.
5 *
6 * @copyright (c) phpBB Limited <https://www.phpbb.com>
7 * @license GNU General Public License, version 2 (GPL-2.0)
8 *
9 * For full copyright and license information, please see
10 * the docs/CREDITS.txt file.
11 *
12 */
13
14namespace phpbb\group;
15
16use phpbb\auth\auth;
17use phpbb\avatar\helper as avatar_helper;
18use phpbb\cache\service as cache;
19use phpbb\config\config;
20use phpbb\db\driver\driver_interface;
21use phpbb\language\language;
22use phpbb\event\dispatcher_interface;
23use phpbb\path_helper;
24use phpbb\template\template;
25use phpbb\user;
26
27class helper
28{
29    /** @var auth */
30    protected $auth;
31
32    /** @var avatar_helper */
33    protected $avatar_helper;
34
35    /** @var driver_interface */
36    protected $db;
37
38    /** @var cache */
39    protected $cache;
40
41    /** @var config */
42    protected $config;
43
44    /** @var language */
45    protected $language;
46
47    /** @var dispatcher_interface */
48    protected $dispatcher;
49
50    /** @var path_helper */
51    protected $path_helper;
52
53    /** @var template */
54    protected $template;
55
56    /** @var user */
57    protected $user;
58
59    /** @var string phpBB root path */
60    protected $phpbb_root_path;
61
62    /** @var array Return templates for a group name string */
63    protected $name_strings;
64
65    /**
66     * Constructor
67     *
68     * @param auth                    $auth            Authentication object
69     * @param avatar_helper            $avatar_helper    Avatar helper object
70     * @param driver_interface         $db             Database connection
71     * @param cache                    $cache            Cache service object
72     * @param config                $config            Configuration object
73     * @param language                $language        Language object
74     * @param dispatcher_interface    $dispatcher        Event dispatcher object
75     * @param path_helper            $path_helper    Path helper object
76     * @param template                 $template         Template service
77     * @param user                    $user            User object
78     */
79    public function __construct(auth $auth, avatar_helper $avatar_helper, driver_interface $db, cache $cache, config $config, language $language, dispatcher_interface $dispatcher, path_helper $path_helper, template $template, user $user)
80    {
81        $this->auth = $auth;
82        $this->avatar_helper = $avatar_helper;
83        $this->db = $db;
84        $this->cache = $cache;
85        $this->config = $config;
86        $this->language = $language;
87        $this->dispatcher = $dispatcher;
88        $this->path_helper = $path_helper;
89        $this->template = $template;
90        $this->user = $user;
91
92        $this->phpbb_root_path = $path_helper->get_phpbb_root_path();
93
94        /** @html Group name spans and links for usage in the template */
95        $this->name_strings = array(
96            'base_url'                => "{$path_helper->get_phpbb_root_path()}memberlist.{$path_helper->get_php_ext()}?mode=group&amp;g={GROUP_ID}",
97            'tpl_noprofile'            => '<span class="username">{GROUP_NAME}</span>',
98            'tpl_noprofile_colour'    => '<span class="username-coloured" style="color: {GROUP_COLOUR};">{GROUP_NAME}</span>',
99            'tpl_profile'            => '<a class="username" href="{PROFILE_URL}">{GROUP_NAME}</a>',
100            'tpl_profile_colour'    => '<a class="username-coloured" href="{PROFILE_URL}" style="color: {GROUP_COLOUR};">{GROUP_NAME}</a>',
101        );
102    }
103
104    /**
105     * @param    string    $group_name    The stored group name
106     *
107     * @return string        Group name or translated group name if it exists
108     */
109    public function get_name($group_name)
110    {
111        return $this->language->is_set('G_' . utf8_strtoupper($group_name)) ? $this->language->lang('G_' . utf8_strtoupper($group_name)) : $group_name;
112    }
113
114    /**
115     * Get group name details for placing into templates.
116     *
117     * @html Group name spans and links
118     *
119     * @param string    $mode                Profile (for getting an url to the profile),
120     *                                            group_name (for obtaining the group name),
121     *                                            colour (for obtaining the group colour),
122     *                                            full (for obtaining a coloured group name link to the group's profile),
123     *                                            no_profile (the same as full but forcing no profile link)
124     * @param int        $group_id            The group id
125     * @param string    $group_name            The group name
126     * @param string    $group_colour        The group colour
127     * @param mixed        $custom_profile_url    optional parameter to specify a profile url. The group id gets appended to this url as &amp;g={group_id}
128     *
129     * @return string A string consisting of what is wanted based on $mode.
130     */
131    public function get_name_string($mode, $group_id, $group_name, $group_colour = '', $custom_profile_url = false)
132    {
133        $s_is_bots = ($group_name === 'BOTS');
134        $group_name_string = null;
135
136        // This switch makes sure we only run code required for the mode
137        switch ($mode)
138        {
139            case 'full':
140            case 'no_profile':
141            case 'colour':
142
143                // Build correct group colour
144                $group_colour = $group_colour ? '#' . $group_colour : '';
145
146                // Return colour
147                if ($mode === 'colour')
148                {
149                    $group_name_string = $group_colour;
150                    break;
151                }
152
153            // no break;
154
155            case 'group_name':
156
157                // Build correct group name
158                $group_name = $this->get_name($group_name);
159
160                // Return group name
161                if ($mode === 'group_name')
162                {
163                    $group_name_string = $group_name;
164                    break;
165                }
166
167            // no break;
168
169            case 'profile':
170
171                // Build correct profile url - only show if not anonymous and permission to view profile if registered user
172                // For anonymous the link leads to a login page.
173                if ($group_id && !$s_is_bots && ($this->user->data['user_id'] == ANONYMOUS || $this->auth->acl_get('u_viewprofile')))
174                {
175                    $profile_url = ($custom_profile_url !== false) ? $custom_profile_url . '&amp;g=' . (int) $group_id : str_replace(array('={GROUP_ID}', '=%7BGROUP_ID%7D'), '=' . (int) $group_id, append_sid($this->name_strings['base_url']));
176                }
177                else
178                {
179                    $profile_url = '';
180                }
181
182                // Return profile
183                if ($mode === 'profile')
184                {
185                    $group_name_string = $profile_url;
186                    break;
187                }
188
189            // no break;
190        }
191
192        if (!isset($group_name_string))
193        {
194            if (($mode === 'full' && empty($profile_url)) || $mode === 'no_profile' || $s_is_bots)
195            {
196                $group_name_string = str_replace(array('{GROUP_COLOUR}', '{GROUP_NAME}'), array($group_colour, $group_name), (!$group_colour) ? $this->name_strings['tpl_noprofile'] : $this->name_strings['tpl_noprofile_colour']);
197            }
198            else
199            {
200                $group_name_string = str_replace(array('{PROFILE_URL}', '{GROUP_COLOUR}', '{GROUP_NAME}'), array($profile_url, $group_colour, $group_name), (!$group_colour) ? $this->name_strings['tpl_profile'] : $this->name_strings['tpl_profile_colour']);
201            }
202        }
203
204        $name_strings = $this->name_strings;
205
206        /**
207         * Use this event to change the output of the group name
208         *
209         * @event core.modify_group_name_string
210         * @var string    mode                profile|group_name|colour|full|no_profile
211         * @var int        group_id            The group identifier
212         * @var string    group_name            The group name
213         * @var string    group_colour        The group colour
214         * @var string    custom_profile_url    Optional parameter to specify a profile url.
215         * @var string    group_name_string    The string that has been generated
216         * @var array    name_strings        Array of original return templates
217         * @since 3.2.8-RC1
218         */
219        $vars = array(
220            'mode',
221            'group_id',
222            'group_name',
223            'group_colour',
224            'custom_profile_url',
225            'group_name_string',
226            'name_strings',
227        );
228        extract($this->dispatcher->trigger_event('core.modify_group_name_string', compact($vars)));
229
230        return $group_name_string;
231    }
232
233    /**
234     * Get group rank title and image
235     *
236     * @html Group rank image element
237     *
238     * @param array        $group_data        The current stored group data
239     *
240     * @return array                    An associative array containing the rank title (title),
241     *                                     the rank image as full img tag (img) and the rank image source (img_src)
242     */
243    public function get_rank($group_data)
244    {
245        $group_rank_data = array(
246            'title'        => null,
247            'img'        => null,
248            'img_src'    => null,
249        );
250
251        /**
252         * Preparing a group's rank before displaying
253         *
254         * @event core.get_group_rank_before
255         * @var    array    group_data        Array with group's data
256         * @since 3.2.8-RC1
257         */
258
259        $vars = array('group_data');
260        extract($this->dispatcher->trigger_event('core.get_group_rank_before', compact($vars)));
261
262        if (!empty($group_data['group_rank']))
263        {
264            // Only obtain ranks if group rank is set
265            $ranks = $this->cache->obtain_ranks();
266
267            if (isset($ranks['special'][$group_data['group_rank']]))
268            {
269                $rank = $ranks['special'][$group_data['group_rank']];
270
271                $group_rank_data['title'] = $rank['rank_title'];
272
273                $group_rank_data['img_src'] = (!empty($rank['rank_image'])) ? $this->path_helper->update_web_root_path($this->phpbb_root_path . $this->config['ranks_path'] . '/' . $rank['rank_image']) : '';
274
275                /** @html Group rank image element for usage in the template */
276                $group_rank_data['img'] = (!empty($rank['rank_image'])) ? '<img src="' . $group_rank_data['img_src'] . '" alt="' . $rank['rank_title'] . '" title="' . $rank['rank_title'] . '" />' : '';
277            }
278        }
279
280        /**
281         * Modify a group's rank before displaying
282         *
283         * @event core.get_group_rank_after
284         * @var    array    group_data        Array with group's data
285         * @var    array    group_rank_data    Group rank data
286         * @since 3.2.8-RC1
287         */
288
289        $vars = array(
290            'group_data',
291            'group_rank_data',
292        );
293        extract($this->dispatcher->trigger_event('core.get_group_rank_after', compact($vars)));
294
295        return $group_rank_data;
296    }
297
298    /**
299     * Get group avatar.
300     * Wrapper function for \phpbb\avatar\helper::get_group_avatar()
301     *
302     * @param array        $group_row        Row from the groups table
303     * @param string    $alt            Optional language string for alt tag within image, can be a language key or text
304     * @param bool        $ignore_config    Ignores the config-setting, to be still able to view the avatar in the UCP
305     * @param bool        $lazy            If true, will be lazy loaded (requires JS)
306     *
307     * @return array                     Avatar data
308     */
309    public function get_avatar($group_row, $alt = 'GROUP_AVATAR', $ignore_config = false, $lazy = false)
310    {
311        return $this->avatar_helper->get_group_avatar($group_row, $alt, $ignore_config, $lazy);
312    }
313
314    /**
315     * Display groups legend
316     *
317     * @return void
318     */
319    public function display_legend(): void
320    {
321        $order_legend = $this->config['legend_sort_groupname'] ? 'group_name' : 'group_legend';
322
323        // Grab group details for legend display
324        if ($this->auth->acl_gets('a_group', 'a_groupadd', 'a_groupdel'))
325        {
326            $sql = 'SELECT group_id, group_name, group_colour, group_type, group_legend
327                FROM ' . GROUPS_TABLE . '
328                WHERE group_legend > 0
329                ORDER BY ' . $order_legend . ' ASC';
330        }
331        else
332        {
333            $sql = 'SELECT g.group_id, g.group_name, g.group_colour, g.group_type, g.group_legend
334                FROM ' . GROUPS_TABLE . ' g
335                LEFT JOIN ' . USER_GROUP_TABLE . ' ug
336                    ON (
337                        g.group_id = ug.group_id
338                        AND ug.user_id = ' . $this->user->data['user_id'] . '
339                        AND ug.user_pending = 0
340                    )
341                WHERE g.group_legend > 0
342                    AND (g.group_type <> ' . GROUP_HIDDEN . ' OR ug.user_id = ' . $this->user->data['user_id'] . ')
343                ORDER BY g.' . $order_legend . ' ASC';
344        }
345        $result = $this->db->sql_query($sql);
346
347        while ($row = $this->db->sql_fetchrow($result))
348        {
349            $show_group_url = $row['group_name'] != 'BOTS' && $this->auth->acl_get('u_viewprofile');
350
351            $this->template->assign_block_vars('LEGEND', [
352                'GROUP_COLOR'        => $row['group_colour'] ?: '',
353                'GROUP_NAME'        => $this->get_name($row['group_name']),
354                'GROUP_URL'            => $show_group_url ? append_sid("{$this->path_helper->get_phpbb_root_path()}memberlist.{$this->path_helper->get_php_ext()}", 'mode=group&amp;g=' . $row['group_id']) : '',
355            ]);
356        }
357        $this->db->sql_freeresult($result);
358    }
359}