*/
private static $Modules = [
'login' => 'ApiLogin',
+ 'clientlogin' => 'ApiClientLogin',
'logout' => 'ApiLogout',
- 'createaccount' => 'ApiCreateAccount',
+ 'createaccount' => 'ApiAMCreateAccount',
+ 'linkaccount' => 'ApiLinkAccount',
+ 'unlinkaccount' => 'ApiRemoveAuthenticationData',
+ 'changeauthenticationdata' => 'ApiChangeAuthenticationData',
+ 'removeauthenticationdata' => 'ApiRemoveAuthenticationData',
+ 'resetpassword' => 'ApiResetPassword',
'query' => 'ApiQuery',
'expandtemplates' => 'ApiExpandTemplates',
'parse' => 'ApiParse',
private $mCacheControl = [];
private $mParamsUsed = [];
+ /** @var bool|null Cached return value from self::lacksSameOriginSecurity() */
+ private $lacksSameOriginSecurity = null;
+
/**
* Constructs an instance of ApiMain that utilizes the module and format specified by $request.
*
return $this->mResult;
}
+ /**
+ * Get the security flag for the current request
+ * @return bool
+ */
+ public function lacksSameOriginSecurity() {
+ if ( $this->lacksSameOriginSecurity !== null ) {
+ return $this->lacksSameOriginSecurity;
+ }
+
+ $request = $this->getRequest();
+
+ // JSONP mode
+ if ( $request->getVal( 'callback' ) !== null ) {
+ $this->lacksSameOriginSecurity = true;
+ return true;
+ }
+
+ // Header to be used from XMLHTTPRequest when the request might
+ // otherwise be used for XSS.
+ if ( $request->getHeader( 'Treat-as-Untrusted' ) !== false ) {
+ $this->lacksSameOriginSecurity = true;
+ return true;
+ }
+
+ // Allow extensions to override.
+ $this->lacksSameOriginSecurity = !Hooks::run( 'RequestHasSameOriginSecurity', array( $request ) );
+ return $this->lacksSameOriginSecurity;
+ }
+
+
/**
* Get the ApiErrorFormatter object associated with current request
* @return ApiErrorFormatter
$response = $this->getRequest()->response();
$out = $this->getOutput();
+ $out->addVaryHeader( 'Treat-as-Untrusted' );
+
$config = $this->getConfig();
if ( $config->get( 'VaryOnXFP' ) ) {
TS_MW, time() - $this->getConfig()->get( 'SquidMaxage' )
);
}
- Hooks::run( 'OutputPageCheckLastModified', [ &$modifiedTimes ] );
+ Hooks::run( 'OutputPageCheckLastModified', [ &$modifiedTimes, $this->getOutput() ] );
$lastMod = max( $modifiedTimes );
$return304 = wfTimestamp( TS_MW, $lastMod ) <= $ts->getTimestamp( TS_MW );
}
return array_keys( $this->mParamsUsed );
}
+ /**
+ * Mark parameters as used
+ * @param string|string[] $params
+ */
+ public function markParamsUsed( $params ) {
+ $this->mParamsUsed += array_fill_keys( (array)$params, true );
+ }
+
/**
* Get a request value, and register the fact that it was used, for logging.
* @param string $name
$tocnumber = &$options['tocnumber'];
$header = $this->msg( 'api-help-datatypes-header' )->parse();
+
+ // Add an additional span with sanitized ID
+ if ( !$this->getConfig()->get( 'ExperimentalHtmlIds' ) ) {
+ $header = Html::element( 'span', [ 'id' => Sanitizer::escapeId( 'main/datatypes' ) ] ) .
+ $header;
+ }
$help['datatypes'] .= Html::rawElement( 'h' . min( 6, $level ),
[ 'id' => 'main/datatypes', 'class' => 'apihelp-header' ],
- Html::element( 'span', [ 'id' => Sanitizer::escapeId( 'main/datatypes' ) ] ) .
$header
);
$help['datatypes'] .= $this->msg( 'api-help-datatypes' )->parseAsBlock();
];
}
+ // Add an additional span with sanitized ID
+ if ( !$this->getConfig()->get( 'ExperimentalHtmlIds' ) ) {
+ $header = Html::element( 'span', [ 'id' => Sanitizer::escapeId( 'main/credits' ) ] ) .
+ $header;
+ }
$header = $this->msg( 'api-credits-header' )->parse();
$help['credits'] .= Html::rawElement( 'h' . min( 6, $level ),
[ 'id' => 'main/credits', 'class' => 'apihelp-header' ],
- Html::element( 'span', [ 'id' => Sanitizer::escapeId( 'main/credits' ) ] ) .
$header
);
$help['credits'] .= $this->msg( 'api-credits' )->useDatabase( false )->parseAsBlock();