From 9d02a8c560a36920d76557c1c06c1b6e754e3845 Mon Sep 17 00:00:00 2001 From: Rotem Liss Date: Sat, 5 Jan 2008 10:05:34 +0000 Subject: [PATCH] Quick solution for problems with limit=max when using slow queries: allowing modules to delay the parsing of limit=max until they get the actual maximum values, and making them parse it by themselves. --- includes/api/ApiBase.php | 18 ++++++++++++------ includes/api/ApiQueryDeletedrevs.php | 15 ++++++++++----- includes/api/ApiQueryRevisions.php | 6 +++++- 3 files changed, 27 insertions(+), 12 deletions(-) diff --git a/includes/api/ApiBase.php b/includes/api/ApiBase.php index da3ad3b304..af2a3b58e7 100644 --- a/includes/api/ApiBase.php +++ b/includes/api/ApiBase.php @@ -303,13 +303,15 @@ abstract class ApiBase { * Using getAllowedParams(), makes an array of the values provided by the user, * with key being the name of the variable, and value - validated value from user or default. * This method can be used to generate local variables using extract(). + * limit=max will not be parsed if $parseMaxLimit is set to false; use this + * when the max limit is not definite, e.g. when getting revisions. */ - public function extractRequestParams() { + public function extractRequestParams($parseMaxLimit = true) { $params = $this->getAllowedParams(); $results = array (); foreach ($params as $paramName => $paramSettings) - $results[$paramName] = $this->getParameterFromSettings($paramName, $paramSettings); + $results[$paramName] = $this->getParameterFromSettings($paramName, $paramSettings, $parseMaxLimit); return $results; } @@ -341,8 +343,9 @@ abstract class ApiBase { * Using the settings determine the value for the given parameter * @param $paramName String: parameter name * @param $paramSettings Mixed: default value or an array of settings using PARAM_* constants. + * @param $parseMaxLimit Boolean: parse limit when max is given? */ - protected function getParameterFromSettings($paramName, $paramSettings) { + protected function getParameterFromSettings($paramName, $paramSettings, $parseMaxLimit) { // Some classes may decide to change parameter names $encParamName = $this->encodeParamName($paramName); @@ -411,13 +414,16 @@ abstract class ApiBase { ApiBase :: dieDebug(__METHOD__, "Multi-values not supported for $encParamName"); $min = isset ($paramSettings[self :: PARAM_MIN]) ? $paramSettings[self :: PARAM_MIN] : 0; if( $value == 'max' ) { - $value = $this->getMain()->canApiHighLimits() ? $paramSettings[self :: PARAM_MAX2] : $paramSettings[self :: PARAM_MAX]; - $this->getResult()->addValue( 'limits', 'limit', $value ); + if( $parseMaxLimit ) { + $value = $this->getMain()->canApiHighLimits() ? $paramSettings[self :: PARAM_MAX2] : $paramSettings[self :: PARAM_MAX]; + $this->getResult()->addValue( 'limits', 'limit', $value ); + $this->validateLimit($paramName, $value, $min, $paramSettings[self :: PARAM_MAX], $paramSettings[self :: PARAM_MAX2]); + } } else { $value = intval($value); + $this->validateLimit($paramName, $value, $min, $paramSettings[self :: PARAM_MAX], $paramSettings[self :: PARAM_MAX2]); } - $this->validateLimit($paramName, $value, $min, $paramSettings[self :: PARAM_MAX], $paramSettings[self :: PARAM_MAX2]); break; case 'boolean' : if ($multi) diff --git a/includes/api/ApiQueryDeletedrevs.php b/includes/api/ApiQueryDeletedrevs.php index 57e7fc0ad8..14dd26b718 100644 --- a/includes/api/ApiQueryDeletedrevs.php +++ b/includes/api/ApiQueryDeletedrevs.php @@ -47,7 +47,7 @@ class ApiQueryDeletedrevs extends ApiQueryBase { $this->dieUsage('You don\'t have permission to view deleted revision information', 'permissiondenied'); $db = $this->getDB(); - $params = $this->extractRequestParams(); + $params = $this->extractRequestParams(false); $prop = array_flip($params['prop']); $fld_revid = isset($prop['revid']); $fld_user = isset($prop['user']); @@ -80,13 +80,18 @@ class ApiQueryDeletedrevs extends ApiQueryBase { $this->addFields(array('ar_text', 'ar_text_id', 'old_text', 'old_flags')); $this->addWhere('ar_text_id = old_id'); - // This also means stricter limits and stricter restrictions + // This also means stricter restrictions if(!$wgUser->isAllowed('undelete')) $this->dieUsage('You don\'t have permission to view deleted revision content', 'permissiondenied'); - $userMax = ApiBase :: LIMIT_SML1; - $botMax = ApiBase :: LIMIT_SML2; - $this->validateLimit('limit', $params['limit'], 1, $userMax, $botMax); } + // Check limits + $userMax = $fld_content ? ApiBase :: LIMIT_SML1 : ApiBase :: LIMIT_BIG1; + $botMax = $fld_content ? ApiBase :: LIMIT_SML2 : ApiBase :: LIMIT_BIG2; + if( $limit == 'max' ) { + $limit = $this->getMain()->canApiHighLimits() ? $botMax : $userMax; + $this->getResult()->addValue( 'limits', 'limit', $limit ); + } + $this->validateLimit('limit', $params['limit'], 1, $userMax, $botMax); if($fld_token) // Undelete tokens are identical for all pages, so we cache one here $token = $wgUser->editToken(); diff --git a/includes/api/ApiQueryRevisions.php b/includes/api/ApiQueryRevisions.php index 4eb0e2a127..14da7f917e 100644 --- a/includes/api/ApiQueryRevisions.php +++ b/includes/api/ApiQueryRevisions.php @@ -46,7 +46,7 @@ class ApiQueryRevisions extends ApiQueryBase { public function execute() { $limit = $startid = $endid = $start = $end = $dir = $prop = $user = $excludeuser = $token = null; - extract($this->extractRequestParams()); + extract($this->extractRequestParams(false)); // If any of those parameters are used, work in 'enumeration' mode. // Enum mode can only be used when exactly one page is provided. @@ -122,6 +122,10 @@ class ApiQueryRevisions extends ApiQueryBase { $userMax = ( $this->fld_content ? ApiBase::LIMIT_SML1 : ApiBase::LIMIT_BIG1 ); $botMax = ( $this->fld_content ? ApiBase::LIMIT_SML2 : ApiBase::LIMIT_BIG2 ); + if( $limit == 'max' ) { + $limit = $this->getMain()->canApiHighLimits() ? $botMax : $userMax; + $this->getResult()->addValue( 'limits', 'limit', $limit ); + } if ($enumRevMode) { -- 2.20.1