Code Coverage
 
Lines
Functions and Methods
Classes and Traits
Total
0.00% covered (danger)
0.00%
0 / 74
0.00% covered (danger)
0.00%
0 / 2
CRAP
0.00% covered (danger)
0.00%
0 / 1
ApiQueryCategoryList
0.00% covered (danger)
0.00%
0 / 74
0.00% covered (danger)
0.00%
0 / 2
380
0.00% covered (danger)
0.00%
0 / 1
 createQuery
0.00% covered (danger)
0.00%
0 / 43
0.00% covered (danger)
0.00%
0 / 1
110
 executeQuery
0.00% covered (danger)
0.00%
0 / 31
0.00% covered (danger)
0.00%
0 / 1
90
1<?php
2
3namespace MediaWiki\Api;
4
5use MediaWiki\Title\Title;
6use Wikimedia\Rdbms\IExpression;
7use Wikimedia\Rdbms\IReadableDatabase;
8use Wikimedia\Rdbms\LikeValue;
9
10abstract class ApiQueryCategoryList extends ApiQueryGeneratorBase {
11
12    protected function createQuery( IReadableDatabase $db, array $params ): void {
13        $this->addTables( 'category' );
14        $this->addFields( 'cat_title' );
15
16        if ( $params['continue'] !== null ) {
17            $cont = $this->parseContinueParamOrDie( $params['continue'], [ 'string' ] );
18            $op = $params['dir'] == 'descending' ? '<=' : '>=';
19            $this->addWhere( $db->expr( 'cat_title', $op, $cont[0] ) );
20        }
21
22        $dir = ( $params['dir'] == 'descending' ? 'older' : 'newer' );
23        $from = ( $params['from'] === null
24            ? null
25            : $this->titlePartToKey( $params['from'], NS_CATEGORY ) );
26        $to = ( $params['to'] === null
27            ? null
28            : $this->titlePartToKey( $params['to'], NS_CATEGORY ) );
29        $this->addWhereRange( 'cat_title', $dir, $from, $to );
30
31        $min = $params['min'];
32        $max = $params['max'];
33        if ( $dir == 'newer' ) {
34            $this->addWhereRange( 'cat_pages', 'newer', $min, $max );
35        } else {
36            $this->addWhereRange( 'cat_pages', 'older', $max, $min );
37        }
38
39        if ( isset( $params['prefix'] ) ) {
40            $this->addWhere(
41                $db->expr(
42                    'cat_title',
43                    IExpression::LIKE,
44                    new LikeValue( $this->titlePartToKey( $params['prefix'], NS_CATEGORY ), $db->anyString() )
45                )
46            );
47        }
48
49        $this->addOption( 'LIMIT', $params['limit'] + 1 );
50        $sort = ( $params['dir'] == 'descending' ? ' DESC' : '' );
51        $this->addOption( 'ORDER BY', 'cat_title' . $sort );
52
53        $prop = array_fill_keys( $params['prop'], true );
54        $this->addFieldsIf( [ 'cat_pages', 'cat_subcats', 'cat_files' ], isset( $prop['size'] ) );
55        if ( isset( $prop['hidden'] ) ) {
56            $this->addTables( [ 'page', 'page_props' ] );
57            $this->addJoinConds( [
58                'page' => [ 'LEFT JOIN', [
59                    'page_namespace' => NS_CATEGORY,
60                    'page_title=cat_title' ] ],
61                'page_props' => [ 'LEFT JOIN', [
62                    'pp_page=page_id',
63                    'pp_propname' => 'hiddencat' ] ],
64            ] );
65            $this->addFields( [ 'cat_hidden' => 'pp_propname' ] );
66        }
67    }
68
69    protected function executeQuery( array $params, ?ApiPageSet $resultPageSet = null, array $options = [] ) {
70        $res = $this->select( __METHOD__ );
71        $pages = [];
72
73        $result = $this->getResult();
74        $count = 0;
75        foreach ( $res as $row ) {
76            if ( ++$count > $params['limit'] ) {
77                // We've reached the one extra which shows that there are
78                // additional cats to be had. Stop here...
79                $this->setContinueEnumParameter( 'continue', $row->cat_title );
80                break;
81            }
82
83            // Normalize titles
84            $titleObj = Title::makeTitle( NS_CATEGORY, $row->cat_title );
85            if ( $resultPageSet !== null ) {
86                $pages[] = $titleObj;
87            } else {
88                $item = [];
89                ApiResult::setContentValue( $item, 'category', $titleObj->getText() );
90                $prop = array_fill_keys( $params['prop'], true );
91                if ( isset( $prop['size'] ) ) {
92                    $item['size'] = (int)$row->cat_pages;
93                    $item['pages'] = $row->cat_pages - $row->cat_subcats - $row->cat_files;
94                    $item['files'] = (int)$row->cat_files;
95                    $item['subcats'] = (int)$row->cat_subcats;
96                }
97                if ( isset( $prop['hidden'] ) ) {
98                    $item['hidden'] = (bool)$row->cat_hidden;
99                }
100                if ( isset( $options['catNames'] ) ) {
101                    $catNameList = $options['catNames'];
102                    $item['catid'] = $catNameList[ $titleObj->getDBkey() ];
103                }
104                $fit = $result->addValue( [ 'query', $this->getModuleName() ], null, $item );
105                if ( !$fit ) {
106                    $this->setContinueEnumParameter( 'continue', $row->cat_title );
107                    break;
108                }
109            }
110        }
111
112        if ( $resultPageSet === null ) {
113            $result->addIndexedTagName( [ 'query', $this->getModuleName() ], 'c' );
114        } else {
115            $resultPageSet->populateFromTitles( $pages );
116        }
117    }
118}