Completed
Push — main ( 2daa48...b5d932 )
by
unknown
08:38
created

PageListGetter::getRandom()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 4

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
dl 0
loc 4
c 0
b 0
f 0
rs 10
cc 1
nc 1
nop 1
1
<?php
2
3
namespace Addwiki\Mediawiki\Api\Service;
4
5
use Addwiki\Mediawiki\Api\Client\SimpleRequest;
6
use Addwiki\Mediawiki\DataModel\Page;
7
use Addwiki\Mediawiki\DataModel\PageIdentifier;
8
use Addwiki\Mediawiki\DataModel\Pages;
9
use Addwiki\Mediawiki\DataModel\Title;
10
11
/**
12
 * @access private
13
 *
14
 * @author Addshore
15
 */
16
class PageListGetter extends Service {
17
18
	/**
19
	 * Get the set of pages in a given category. Extra parameters can include:
20
	 *     cmtype: default 'page|subcat|file'
21
	 *     cmlimit: default 10, maximum 500 (5000 for bots)
22
	 *
23
	 * @link https://www.mediawiki.org/wiki/API:Categorymembers
24
	 * @since 0.3
25
	 *
26
	 *
27
	 */
28
	public function getPageListFromCategoryName( string $name, array $extraParams = [] ): Pages {
29
		$params = array_merge( $extraParams, [
30
			'list' => 'categorymembers',
31
			'cmtitle' => $name,
32
		] );
33
		return $this->runQuery( $params, 'cmcontinue', 'categorymembers' );
34
	}
35
36
	/**
37
	 * List pages that transclude a certain page.
38
	 *
39
	 * @link https://www.mediawiki.org/wiki/API:Embeddedin
40
	 * @since 0.5
41
	 *
42
	 *
43
	 */
44
	public function getPageListFromPageTransclusions( string $pageName, array $extraParams = [] ): Pages {
45
		$params = array_merge( $extraParams, [
46
			'list' => 'embeddedin',
47
			'eititle' => $pageName,
48
		] );
49
		return $this->runQuery( $params, 'eicontinue', 'embeddedin' );
50
	}
51
52
	/**
53
	 * Get all pages that link to the given page.
54
	 *
55
	 * @link https://www.mediawiki.org/wiki/API:Linkshere
56
	 * @since 0.5
57
	 *
58
	 * @param string $pageName The page name
59
	 * @param string[] $extraParams Any extra parameters to use
60
	 *                 glhprop, glhnamespace, glhshow, glhlimit
61
	 */
62
	public function getFromWhatLinksHere( string $pageName, array $extraParams = [] ): Pages {
63
		$params = array_merge( $extraParams, [
64
			'prop' => 'info',
65
			'generator' => 'linkshere',
66
			'titles' => $pageName,
67
		] );
68
		return $this->runQuery( $params, 'glhcontinue', 'pages' );
69
	}
70
71
	/**
72
	 * Get all pages that are linked to from the given page.
73
	 *
74
	 * @link https://www.mediawiki.org/wiki/API:Links
75
	 *
76
	 * @param string $pageName The page name
77
	 * @param string[] $extraParams Any extra parameters to use
78
	 *                 gpltitles, gplnamespace, gpldir, gpllimit
79
	 */
80
	public function getLinksFromHere( string $pageName, array $extraParams = [] ): Pages {
81
		$params = array_merge( $extraParams, [
82
			'prop' => 'info',
83
			'generator' => 'links',
84
			'titles' => $pageName,
85
		] );
86
		return $this->runQuery( $params, 'gplcontinue', 'pages' );
87
	}
88
89
	/**
90
	 * Get all pages that have the given prefix.
91
	 *
92
	 * @link https://www.mediawiki.org/wiki/API:Allpages
93
	 *
94
	 * @param string $prefix The page title prefix.
95
	 */
96
	public function getFromPrefix( string $prefix ): Pages {
97
		$params = [
98
			'list' => 'allpages',
99
			'apprefix' => $prefix,
100
		];
101
		return $this->runQuery( $params, 'apcontinue', 'allpages' );
102
	}
103
104
	/**
105
	 * Get up to 10 random pages.
106
	 *
107
	 * @link https://www.mediawiki.org/wiki/API:Random
108
	 *
109
	 * @param array $extraParams
110
	 */
111
	public function getRandom( array $extraParams = [] ): Pages {
112
		$params = array_merge( $extraParams, [ 'list' => 'random' ] );
113
		return $this->runQuery( $params, null, 'random', 'id', false );
114
	}
115
116
	/**
117
	 * Run a query to completion.
118
	 *
119
	 * @param string[] $params Query parameters
120
	 * @param string|null $contName Result subelement name for continue details
121
	 * @param string $resName Result element name for main results array
122
	 * @param string $pageIdName Result element name for page ID
123
	 * @param bool $cont Whether to continue the query, using multiple requests
124
	 */
125
	protected function runQuery( array $params, ?string $contName, string $resName, string $pageIdName = 'pageid', bool $cont = true ): Pages {
126
		$pages = new Pages();
127
		$negativeId = -1;
128
129
		$result = [];
130
		do {
131
			// Set up continue parameter if it's been set already.
132
			if ( isset( $result['continue'][$contName] ) ) {
133
				$params[$contName] = $result['continue'][$contName];
134
			}
135
136
			// Run the actual query.
137
			$result = $this->api->getRequest( new SimpleRequest( 'query', $params ) );
138
			if ( !array_key_exists( 'query', $result ) ) {
139
				return $pages;
140
			}
141
142
			// Add the results to the output page list.
143
			foreach ( $result['query'][$resName] as $member ) {
144
				// Assign negative pageid if page is non-existent.
145
				if ( !array_key_exists( $pageIdName, $member ) ) {
146
					$member[$pageIdName] = $negativeId;
147
					--$negativeId;
148
				}
149
150
				$pageTitle = new Title( $member['title'], $member['ns'] );
151
				$page = new Page( new PageIdentifier( $pageTitle, $member[$pageIdName] ) );
152
				$pages->addPage( $page );
153
			}
154
155
		} while ( $cont && isset( $result['continue'] ) );
156
157
		return $pages;
158
	}
159
}
160