Code Coverage
 
Lines
Functions and Methods
Classes and Traits
Total
89.66% covered (warning)
89.66%
26 / 29
50.00% covered (danger)
50.00%
1 / 2
CRAP
0.00% covered (danger)
0.00%
0 / 1
ApiQueryBlockInfoTrait
92.86% covered (success)
92.86%
26 / 28
50.00% covered (danger)
50.00%
1 / 2
8.02
0.00% covered (danger)
0.00%
0 / 1
 addDeletedUserFilter
100.00% covered (success)
100.00%
11 / 11
100.00% covered (success)
100.00%
1 / 1
2
 getBlockDetailsForRows
88.24% covered (warning)
88.24%
15 / 17
0.00% covered (danger)
0.00%
0 / 1
6.06
 getDB
n/a
0 / 0
n/a
0 / 0
0
 getAuthority
n/a
0 / 0
n/a
0 / 0
0
 addTables
n/a
0 / 0
n/a
0 / 0
0
 addFields
n/a
0 / 0
n/a
0 / 0
0
 addWhere
n/a
0 / 0
n/a
0 / 0
0
 addJoinConds
n/a
0 / 0
n/a
0 / 0
0
 getQueryBuilder
n/a
0 / 0
n/a
0 / 0
0
1<?php
2/**
3 * @license GPL-2.0-or-later
4 * @file
5 */
6
7namespace MediaWiki\Api;
8
9use MediaWiki\Block\CompositeBlock;
10use MediaWiki\Block\HideUserUtils;
11use MediaWiki\MediaWikiServices;
12use MediaWiki\Permissions\Authority;
13use stdClass;
14use Wikimedia\Rdbms\IExpression;
15use Wikimedia\Rdbms\IReadableDatabase;
16use Wikimedia\Rdbms\IResultWrapper;
17use Wikimedia\Rdbms\SelectQueryBuilder;
18
19/**
20 * @ingroup API
21 */
22trait ApiQueryBlockInfoTrait {
23    use ApiBlockInfoTrait;
24
25    /**
26     * Filter hidden users if the current user does not have the ability to
27     * view them. Also add a field hu_deleted which will be true if the user
28     * is hidden.
29     *
30     * @since 1.42
31     */
32    private function addDeletedUserFilter() {
33        // TODO: inject dependencies the way ApiWatchlistTrait does
34        $utils = MediaWikiServices::getInstance()->getHideUserUtils();
35        if ( !$this->getAuthority()->isAllowed( 'hideuser' ) ) {
36            $this->addWhere( $utils->getExpression( $this->getDB() ) );
37            // The field is always false since we are filtering out rows where it is true
38            $this->addFields( [ 'hu_deleted' => '1=0' ] );
39        } else {
40            $this->addFields( [
41                'hu_deleted' => $utils->getExpression(
42                    $this->getDB(),
43                    'user_id',
44                    HideUserUtils::HIDDEN_USERS
45                )
46            ] );
47        }
48    }
49
50    /**
51     * For a set of rows with a user_id field, get the block details for all
52     * users, and return them in array, formatted using
53     * ApiBlockInfoTrait::getBlockDetails().
54     *
55     * @since 1.42
56     * @param iterable<stdClass>|IResultWrapper $rows Rows with a user_id field
57     * @return array The block details indexed by user_id. If a user is not blocked,
58     *   the key will be absent.
59     */
60    private function getBlockDetailsForRows( $rows ) {
61        $ids = [];
62        foreach ( $rows as $row ) {
63            $ids[] = (int)$row->user_id;
64        }
65        if ( !$ids ) {
66            return [];
67        }
68        $blocks = MediaWikiServices::getInstance()->getDatabaseBlockStore()
69            ->newListFromConds( [ 'bt_user' => $ids ] );
70        $blocksByUser = [];
71        foreach ( $blocks as $block ) {
72            $blocksByUser[$block->getTargetUserIdentity()->getId()][] = $block;
73        }
74        $infoByUser = [];
75        foreach ( $blocksByUser as $id => $userBlocks ) {
76            if ( count( $userBlocks ) > 1 ) {
77                $maybeCompositeBlock = CompositeBlock::createFromBlocks( ...$userBlocks );
78            } else {
79                $maybeCompositeBlock = $userBlocks[0];
80            }
81            $infoByUser[$id] = $this->getBlockDetails( $maybeCompositeBlock );
82        }
83        return $infoByUser;
84    }
85
86    /***************************************************************************/
87    // region   Methods required from ApiQueryBase
88    /** @name   Methods required from ApiQueryBase */
89
90    /**
91     * @see ApiBase::getDB
92     * @return IReadableDatabase
93     */
94    abstract protected function getDB();
95
96    /**
97     * @see IContextSource::getAuthority
98     * @return Authority
99     */
100    abstract public function getAuthority();
101
102    /**
103     * @see ApiQueryBase::addTables
104     * @param string|array $tables
105     * @param string|null $alias
106     */
107    abstract protected function addTables( $tables, $alias = null );
108
109    /**
110     * @see ApiQueryBase::addFields
111     * @param array|string $fields
112     */
113    abstract protected function addFields( $fields );
114
115    /**
116     * @see ApiQueryBase::addWhere
117     * @param string|array|IExpression $conds
118     */
119    abstract protected function addWhere( $conds );
120
121    /**
122     * @see ApiQueryBase::addJoinConds
123     * @param array $conds
124     */
125    abstract protected function addJoinConds( $conds );
126
127    /**
128     * @return SelectQueryBuilder
129     */
130    abstract protected function getQueryBuilder();
131
132    // endregion -- end of methods required from ApiQueryBase
133
134}
135
136/** @deprecated class alias since 1.43 */
137class_alias( ApiQueryBlockInfoTrait::class, 'ApiQueryBlockInfoTrait' );