MediaWiki REL1_41
SearchApi.php
Go to the documentation of this file.
1<?php
2
25
30trait SearchApi {
31
32 private SearchEngineConfig $searchEngineConfig;
33 private SearchEngineFactory $searchEngineFactory;
34
35 private function checkDependenciesSet() {
36 // Since this is a trait, we can't have a constructor where the services
37 // that we need are injected. Instead, the api modules that use this trait
38 // are responsible for setting them (since api modules *can* have services
39 // injected). Double check that the api module did indeed set them
40 // @phan-suppress-next-line PhanRedundantCondition Phan trusts the type hints too much
41 if ( !isset( $this->searchEngineConfig ) || !isset( $this->searchEngineFactory ) ) {
42 throw new LogicException(
43 'SearchApi requires both a SearchEngineConfig and SearchEngineFactory to be set'
44 );
45 }
46 }
47
54 private static $BACKEND_NULL_PARAM = 'database-backed';
55
64 public function buildCommonApiParams( $isScrollable = true ) {
65 $this->checkDependenciesSet();
66
67 $params = [
68 'search' => [
69 ParamValidator::PARAM_TYPE => 'string',
70 ParamValidator::PARAM_REQUIRED => true,
71 ],
72 'namespace' => [
73 ParamValidator::PARAM_DEFAULT => NS_MAIN,
74 ParamValidator::PARAM_TYPE => 'namespace',
75 ParamValidator::PARAM_ISMULTI => true,
76 ],
77 'limit' => [
78 ParamValidator::PARAM_DEFAULT => 10,
79 ParamValidator::PARAM_TYPE => 'limit',
80 IntegerDef::PARAM_MIN => 1,
81 IntegerDef::PARAM_MAX => ApiBase::LIMIT_BIG1,
82 IntegerDef::PARAM_MAX2 => ApiBase::LIMIT_BIG2,
83 ],
84 ];
85 if ( $isScrollable ) {
86 $params['offset'] = [
87 ParamValidator::PARAM_DEFAULT => 0,
88 IntegerDef::PARAM_MIN => 0,
89 ParamValidator::PARAM_TYPE => 'integer',
90 ApiBase::PARAM_HELP_MSG => 'api-help-param-continue',
91 ];
92 }
93
94 $alternatives = $this->searchEngineConfig->getSearchTypes();
95 if ( count( $alternatives ) > 1 ) {
96 $alternatives[0] ??= self::$BACKEND_NULL_PARAM;
97 $params['backend'] = [
98 ParamValidator::PARAM_DEFAULT => $this->searchEngineConfig->getSearchType(),
99 ParamValidator::PARAM_TYPE => $alternatives,
100 ];
101 // @todo: support profile selection when multiple
102 // backends are available. The solution could be to
103 // merge all possible profiles and let ApiBase
104 // subclasses do the check. Making ApiHelp and ApiSandbox
105 // comprehensive might be more difficult.
106 } else {
107 $params += $this->buildProfileApiParam();
108 }
109
110 return $params;
111 }
112
121 private function buildProfileApiParam() {
122 $this->checkDependenciesSet();
123
124 $configs = $this->getSearchProfileParams();
125 $searchEngine = $this->searchEngineFactory->create();
126 $params = [];
127 foreach ( $configs as $paramName => $paramConfig ) {
128 $profiles = $searchEngine->getProfiles(
129 $paramConfig['profile-type'],
130 $this->getContext()->getUser()
131 );
132 if ( !$profiles ) {
133 continue;
134 }
135
136 $types = [];
137 $helpMessages = [];
138 $defaultProfile = null;
139 foreach ( $profiles as $profile ) {
140 $types[] = $profile['name'];
141 if ( isset( $profile['desc-message'] ) ) {
142 $helpMessages[$profile['name']] = $profile['desc-message'];
143 }
144
145 if ( !empty( $profile['default'] ) ) {
146 $defaultProfile = $profile['name'];
147 }
148 }
149
150 $params[$paramName] = [
151 ParamValidator::PARAM_TYPE => $types,
152 ApiBase::PARAM_HELP_MSG => $paramConfig['help-message'],
153 ApiBase::PARAM_HELP_MSG_PER_VALUE => $helpMessages,
154 ParamValidator::PARAM_DEFAULT => $defaultProfile,
155 ];
156 }
157
158 return $params;
159 }
160
174 public function buildSearchEngine( array $params = null ) {
175 $this->checkDependenciesSet();
176
177 if ( $params == null ) {
178 return $this->searchEngineFactory->create();
179 }
180
181 $type = $params['backend'] ?? null;
182 if ( $type === self::$BACKEND_NULL_PARAM ) {
183 $type = null;
184 }
185 $searchEngine = $this->searchEngineFactory->create( $type );
186 $searchEngine->setNamespaces( $params['namespace'] );
187 $searchEngine->setLimitOffset( $params['limit'], $params['offset'] ?? 0 );
188
189 // Initialize requested search profiles.
190 $configs = $this->getSearchProfileParams();
191 foreach ( $configs as $paramName => $paramConfig ) {
192 if ( isset( $params[$paramName] ) ) {
193 $searchEngine->setFeatureData(
194 $paramConfig['profile-type'],
195 $params[$paramName]
196 );
197 }
198 }
199 return $searchEngine;
200 }
201
206 abstract public function getSearchProfileParams();
207
211 abstract public function getContext();
212}
getUser()
const NS_MAIN
Definition Defines.php:64
getSearchProfileParams()
buildSearchEngine(array $params=null)
Build the search engine to use.
buildCommonApiParams( $isScrollable=true)
The set of api parameters that are shared between api calls that call the SearchEngine.
Definition SearchApi.php:64
getContext()
const PARAM_HELP_MSG_PER_VALUE
((string|array|Message)[]) When PARAM_TYPE is an array, or 'string' with PARAM_ISMULTI,...
Definition ApiBase.php:209
const PARAM_HELP_MSG
(string|array|Message) Specify an alternative i18n documentation message for this parameter.
Definition ApiBase.php:169
Configuration handling class for SearchEngine.
Factory class for SearchEngine.
Service for formatting and validating API parameters.
Type definition for integer types.
trait SearchApi
Traits for API components that use a SearchEngine.
Definition SearchApi.php:30