X-Git-Url: https://git.heureux-cyclage.org/?a=blobdiff_plain;f=includes%2Fapi%2FApiQueryBase.php;h=318af58c55ba52c0fc1c69d70332cb5d7d105f74;hb=9964ca1a390c446397dcd466916ffed356cdc3c9;hp=01968c2a4fb83610a8de5996973ce2028990176e;hpb=466962bd4bf8c8b649eb168b3d8afe189c5b42bf;p=lhc%2Fweb%2Fwiklou.git diff --git a/includes/api/ApiQueryBase.php b/includes/api/ApiQueryBase.php index 01968c2a4f..bba53755c1 100644 --- a/includes/api/ApiQueryBase.php +++ b/includes/api/ApiQueryBase.php @@ -103,7 +103,7 @@ abstract class ApiQueryBase extends ApiBase { /** * Get the Query database connection (read-only) - * @return DatabaseBase + * @return Database */ protected function getDB() { if ( is_null( $this->mDb ) ) { @@ -119,7 +119,7 @@ abstract class ApiQueryBase extends ApiBase { * @param string $name Name to assign to the database connection * @param int $db One of the DB_* constants * @param array $groups Query groups - * @return DatabaseBase + * @return Database */ public function selectNamedDB( $name, $db, $groups ) { $this->mDb = $this->getQuery()->getNamedDB( $name, $db, $groups ); @@ -145,11 +145,11 @@ abstract class ApiQueryBase extends ApiBase { * Blank the internal arrays with query parameters */ protected function resetQueryParams() { - $this->tables = array(); - $this->where = array(); - $this->fields = array(); - $this->options = array(); - $this->join_conds = array(); + $this->tables = []; + $this->where = []; + $this->fields = []; + $this->options = []; + $this->join_conds = []; } /** @@ -176,10 +176,9 @@ abstract class ApiQueryBase extends ApiBase { /** * Add a set of JOIN conditions to the internal array * - * JOIN conditions are formatted as array( tablename => array(jointype, - * conditions) e.g. array('page' => array('LEFT JOIN', - * 'page_id=rev_page')) . conditions may be a string or an - * addWhere()-style array + * JOIN conditions are formatted as [ tablename => [ jointype, conditions ] ] + * e.g. [ 'page' => [ 'LEFT JOIN', 'page_id=rev_page' ] ]. + * Conditions may be a string or an addWhere()-style array. * @param array $join_conds JOIN conditions */ protected function addJoinConds( $join_conds ) { @@ -219,12 +218,12 @@ abstract class ApiQueryBase extends ApiBase { /** * Add a set of WHERE clauses to the internal array. - * Clauses can be formatted as 'foo=bar' or array('foo' => 'bar'), + * Clauses can be formatted as 'foo=bar' or [ 'foo' => 'bar' ], * the latter only works if the value is a constant (i.e. not another field) * * If $value is an empty array, this function does nothing. * - * For example, array('foo=bar', 'baz' => 3, 'bla' => 'foo') translates + * For example, [ 'foo=bar', 'baz' => 3, 'bla' => 'foo' ] translates * to "foo=bar AND baz='3' AND bla='foo'" * @param string|array $value */ @@ -300,7 +299,7 @@ abstract class ApiQueryBase extends ApiBase { // Append ORDER BY $optionOrderBy = isset( $this->options['ORDER BY'] ) ? (array)$this->options['ORDER BY'] - : array(); + : []; $optionOrderBy[] = $order; $this->addOption( 'ORDER BY', $optionOrderBy ); } @@ -341,43 +340,73 @@ abstract class ApiQueryBase extends ApiBase { * @param string $method Function the query should be attributed to. * You should usually use __METHOD__ here * @param array $extraQuery Query data to add but not store in the object - * Format is array( + * Format is [ * 'tables' => ..., * 'fields' => ..., * 'where' => ..., * 'options' => ..., * 'join_conds' => ... - * ) + * ] + * @param array|null &$hookData If set, the ApiQueryBaseBeforeQuery and + * ApiQueryBaseAfterQuery hooks will be called, and the + * ApiQueryBaseProcessRow hook will be expected. * @return ResultWrapper */ - protected function select( $method, $extraQuery = array() ) { + protected function select( $method, $extraQuery = [], array &$hookData = null ) { $tables = array_merge( $this->tables, - isset( $extraQuery['tables'] ) ? (array)$extraQuery['tables'] : array() + isset( $extraQuery['tables'] ) ? (array)$extraQuery['tables'] : [] ); $fields = array_merge( $this->fields, - isset( $extraQuery['fields'] ) ? (array)$extraQuery['fields'] : array() + isset( $extraQuery['fields'] ) ? (array)$extraQuery['fields'] : [] ); $where = array_merge( $this->where, - isset( $extraQuery['where'] ) ? (array)$extraQuery['where'] : array() + isset( $extraQuery['where'] ) ? (array)$extraQuery['where'] : [] ); $options = array_merge( $this->options, - isset( $extraQuery['options'] ) ? (array)$extraQuery['options'] : array() + isset( $extraQuery['options'] ) ? (array)$extraQuery['options'] : [] ); $join_conds = array_merge( $this->join_conds, - isset( $extraQuery['join_conds'] ) ? (array)$extraQuery['join_conds'] : array() + isset( $extraQuery['join_conds'] ) ? (array)$extraQuery['join_conds'] : [] ); + if ( $hookData !== null ) { + Hooks::run( 'ApiQueryBaseBeforeQuery', + [ $this, &$tables, &$fields, &$where, &$options, &$join_conds, &$hookData ] + ); + } + $res = $this->getDB()->select( $tables, $fields, $where, $method, $options, $join_conds ); + if ( $hookData !== null ) { + Hooks::run( 'ApiQueryBaseAfterQuery', [ $this, $res, &$hookData ] ); + } + return $res; } + /** + * Call the ApiQueryBaseProcessRow hook + * + * Generally, a module that passed $hookData to self::select() will call + * this just before calling ApiResult::addValue(), and treat a false return + * here in the same way it treats a false return from addValue(). + * + * @since 1.28 + * @param object $row Database row + * @param array &$data Data to be added to the result + * @param array &$hookData Hook data from ApiQueryBase::select() + * @return bool Return false if row processing should end with continuation + */ + protected function processRow( $row, array &$data, array &$hookData ) { + return Hooks::run( 'ApiQueryBaseProcessRow', [ $this, $row, &$data, &$hookData ] ); + } + /** * @param string $query * @param string $protocol @@ -414,21 +443,21 @@ abstract class ApiQueryBase extends ApiBase { */ public function showHiddenUsersAddBlockInfo( $showBlockInfo ) { $this->addTables( 'ipblocks' ); - $this->addJoinConds( array( - 'ipblocks' => array( 'LEFT JOIN', 'ipb_user=user_id' ), - ) ); + $this->addJoinConds( [ + 'ipblocks' => [ 'LEFT JOIN', 'ipb_user=user_id' ], + ] ); $this->addFields( 'ipb_deleted' ); if ( $showBlockInfo ) { - $this->addFields( array( + $this->addFields( [ 'ipb_id', 'ipb_by', 'ipb_by_text', 'ipb_reason', 'ipb_expiry', 'ipb_timestamp' - ) ); + ] ); } // Don't show hidden names @@ -466,7 +495,7 @@ abstract class ApiQueryBase extends ApiBase { $result = $this->getResult(); ApiResult::setIndexedTagName( $data, $this->getModulePrefix() ); - return $result->addValue( array( 'query', 'pages', intval( $pageId ) ), + return $result->addValue( [ 'query', 'pages', intval( $pageId ) ], $this->getModuleName(), $data ); } @@ -484,13 +513,13 @@ abstract class ApiQueryBase extends ApiBase { $elemname = $this->getModulePrefix(); } $result = $this->getResult(); - $fit = $result->addValue( array( 'query', 'pages', $pageId, - $this->getModuleName() ), null, $item ); + $fit = $result->addValue( [ 'query', 'pages', $pageId, + $this->getModuleName() ], null, $item ); if ( !$fit ) { return false; } - $result->addIndexedTagName( array( 'query', 'pages', $pageId, - $this->getModuleName() ), $elemname ); + $result->addIndexedTagName( [ 'query', 'pages', $pageId, + $this->getModuleName() ], $elemname ); return true; } @@ -518,7 +547,7 @@ abstract class ApiQueryBase extends ApiBase { $t = Title::makeTitleSafe( $namespace, $titlePart . 'x' ); if ( !$t || $t->hasFragment() ) { // Invalid title (e.g. bad chars) or contained a '#'. - $this->dieUsageMsg( array( 'invalidtitle', $titlePart ) ); + $this->dieUsageMsg( [ 'invalidtitle', $titlePart ] ); } if ( $namespace != $t->getNamespace() || $t->isExternal() ) { // This can happen in two cases. First, if you call titlePartToKey with a title part @@ -526,7 +555,7 @@ abstract class ApiQueryBase extends ApiBase { // difficult to handle such a case. Such cases cannot exist and are therefore treated // as invalid user input. The second case is when somebody specifies a title interwiki // prefix. - $this->dieUsageMsg( array( 'invalidtitle', $titlePart ) ); + $this->dieUsageMsg( [ 'invalidtitle', $titlePart ] ); } return substr( $t->getDBkey(), 0, -1 ); @@ -544,10 +573,10 @@ abstract class ApiQueryBase extends ApiBase { $t = Title::newFromText( $titlePart . 'x', $defaultNamespace ); if ( !$t || $t->hasFragment() || $t->isExternal() ) { // Invalid title (e.g. bad chars) or contained a '#'. - $this->dieUsageMsg( array( 'invalidtitle', $titlePart ) ); + $this->dieUsageMsg( [ 'invalidtitle', $titlePart ] ); } - return array( $t->getNamespace(), substr( $t->getDBkey(), 0, -1 ) ); + return [ $t->getNamespace(), substr( $t->getDBkey(), 0, -1 ) ]; } /** @@ -581,182 +610,4 @@ abstract class ApiQueryBase extends ApiBase { } /**@}*/ - - /************************************************************************//** - * @name Deprecated - * @{ - */ - - /** - * Estimate the row count for the SELECT query that would be run if we - * called select() right now, and check if it's acceptable. - * @deprecated since 1.24 - * @return bool True if acceptable, false otherwise - */ - protected function checkRowCount() { - wfDeprecated( __METHOD__, '1.24' ); - $db = $this->getDB(); - $rowcount = $db->estimateRowCount( - $this->tables, - $this->fields, - $this->where, - __METHOD__, - $this->options - ); - - if ( $rowcount > $this->getConfig()->get( 'APIMaxDBRows' ) ) { - return false; - } - - return true; - } - - /** - * Convert a title to a DB key - * @deprecated since 1.24, past uses of this were always incorrect and should - * have used self::titlePartToKey() instead - * @param string $title Page title with spaces - * @return string Page title with underscores - */ - public function titleToKey( $title ) { - wfDeprecated( __METHOD__, '1.24' ); - // Don't throw an error if we got an empty string - if ( trim( $title ) == '' ) { - return ''; - } - $t = Title::newFromText( $title ); - if ( !$t ) { - $this->dieUsageMsg( array( 'invalidtitle', $title ) ); - } - - return $t->getPrefixedDBkey(); - } - - /** - * The inverse of titleToKey() - * @deprecated since 1.24, unused and probably never needed - * @param string $key Page title with underscores - * @return string Page title with spaces - */ - public function keyToTitle( $key ) { - wfDeprecated( __METHOD__, '1.24' ); - // Don't throw an error if we got an empty string - if ( trim( $key ) == '' ) { - return ''; - } - $t = Title::newFromDBkey( $key ); - // This really shouldn't happen but we gotta check anyway - if ( !$t ) { - $this->dieUsageMsg( array( 'invalidtitle', $key ) ); - } - - return $t->getPrefixedText(); - } - - /** - * Inverse of titlePartToKey() - * @deprecated since 1.24, unused and probably never needed - * @param string $keyPart DBkey, with prefix - * @return string Key part with underscores - */ - public function keyPartToTitle( $keyPart ) { - wfDeprecated( __METHOD__, '1.24' ); - return substr( $this->keyToTitle( $keyPart . 'x' ), 0, -1 ); - } - - /** - * Gets the personalised direction parameter description - * - * @deprecated since 1.25 along with ApiBase::getParamDescription - * @param string $p ModulePrefix - * @param string $extraDirText Any extra text to be appended on the description - * @return array - */ - public function getDirectionDescription( $p = '', $extraDirText = '' ) { - return array( - "In which direction to enumerate{$extraDirText}", - " newer - List oldest first. Note: {$p}start has to be before {$p}end.", - " older - List newest first (default). Note: {$p}start has to be later than {$p}end.", - ); - } - - /**@}*/ -} - -/** - * @ingroup API - */ -abstract class ApiQueryGeneratorBase extends ApiQueryBase { - - private $mGeneratorPageSet = null; - - /** - * Switch this module to generator mode. By default, generator mode is - * switched off and the module acts like a normal query module. - * @since 1.21 requires pageset parameter - * @param ApiPageSet $generatorPageSet ApiPageSet object that the module will get - * by calling getPageSet() when in generator mode. - */ - public function setGeneratorMode( ApiPageSet $generatorPageSet ) { - if ( $generatorPageSet === null ) { - ApiBase::dieDebug( __METHOD__, 'Required parameter missing - $generatorPageSet' ); - } - $this->mGeneratorPageSet = $generatorPageSet; - } - - /** - * Get the PageSet object to work on. - * If this module is generator, the pageSet object is different from other module's - * @return ApiPageSet - */ - protected function getPageSet() { - if ( $this->mGeneratorPageSet !== null ) { - return $this->mGeneratorPageSet; - } - - return parent::getPageSet(); - } - - /** - * Overrides ApiBase to prepend 'g' to every generator parameter - * @param string $paramName Parameter name - * @return string Prefixed parameter name - */ - public function encodeParamName( $paramName ) { - if ( $this->mGeneratorPageSet !== null ) { - return 'g' . parent::encodeParamName( $paramName ); - } else { - return parent::encodeParamName( $paramName ); - } - } - - /** - * Overridden to set the generator param if in generator mode - * @param string $paramName Parameter name - * @param string|array $paramValue Parameter value - */ - protected function setContinueEnumParameter( $paramName, $paramValue ) { - if ( $this->mGeneratorPageSet !== null ) { - $this->getContinuationManager()->addGeneratorContinueParam( $this, $paramName, $paramValue ); - } else { - parent::setContinueEnumParameter( $paramName, $paramValue ); - } - } - - /** - * @see ApiBase::getHelpFlags() - * - * Corresponding messages: api-help-flag-generator - */ - protected function getHelpFlags() { - $flags = parent::getHelpFlags(); - $flags[] = 'generator'; - return $flags; - } - - /** - * Execute this module as a generator - * @param ApiPageSet $resultPageSet All output should be appended to this object - */ - abstract public function executeGenerator( $resultPageSet ); }