* @author Roan Kattouw
*/
+use MediaWiki\MediaWikiServices;
+
/**
* Module for ResourceLoader initialization.
*
return $this->configVars[$hash];
}
- global $wgContLang;
$conf = $this->getConfig();
// We can't use Title::newMainPage() if 'mainpage' is in
* - wgNamespaceIds: Key-value pairs of all localized, canonical and aliases for namespaces.
* - wgCaseSensitiveNamespaces: Array of namespaces that are case-sensitive.
*/
- $namespaceIds = $wgContLang->getNamespaceIds();
+ $contLang = MediaWikiServices::getInstance()->getContentLanguage();
+ $namespaceIds = $contLang->getNamespaceIds();
$caseSensitiveNamespaces = [];
foreach ( MWNamespace::getCanonicalNamespaces() as $index => $name ) {
- $namespaceIds[$wgContLang->lc( $name )] = $index;
+ $namespaceIds[$contLang->lc( $name )] = $index;
if ( !MWNamespace::isCapitalized( $index ) ) {
$caseSensitiveNamespaces[] = $index;
}
'wgServer' => $conf->get( 'Server' ),
'wgServerName' => $conf->get( 'ServerName' ),
'wgUserLanguage' => $context->getLanguage(),
- 'wgContentLanguage' => $wgContLang->getCode(),
+ 'wgContentLanguage' => $contLang->getCode(),
'wgTranslateNumerals' => $conf->get( 'TranslateNumerals' ),
'wgVersion' => $conf->get( 'Version' ),
'wgEnableAPI' => true, // Deprecated since MW 1.32
'wgEnableWriteAPI' => true, // Deprecated since MW 1.32
'wgMainPageTitle' => $mainPage->getPrefixedText(),
- 'wgFormattedNamespaces' => $wgContLang->getFormattedNamespaces(),
+ 'wgFormattedNamespaces' => $contLang->getFormattedNamespaces(),
'wgNamespaceIds' => $namespaceIds,
'wgContentNamespaces' => MWNamespace::getContentNamespaces(),
'wgSiteName' => $conf->get( 'Sitename' ),
return true;
}
- /**
- * @param ResourceLoaderContext $context
- * @return array
- */
- public function getPreloadLinks( ResourceLoaderContext $context ) {
- $url = $this->getBaseModulesUrl( $context );
- return [
- $url => [ 'as' => 'script' ]
- ];
- }
-
/**
* Internal modules used by ResourceLoader that cannot be depended on.
*
return [];
}
+ /**
+ * @private For internal use by SpecialJavaScriptTest
+ * @since 1.32
+ * @return array
+ */
+ public function getBaseModulesInternal() {
+ return $this->getBaseModules();
+ }
+
/**
* Base modules implicitly available to all modules.
*
- * @since 1.32
* @return array
*/
private function getBaseModules() {
return $baseModules;
}
- /**
- * Get the load URL of the startup modules.
- *
- * This is a helper for getScript().
- *
- * @param ResourceLoaderContext $context
- * @return string
- */
- private function getBaseModulesUrl( ResourceLoaderContext $context ) {
- $rl = $context->getResourceLoader();
- $derivative = new DerivativeResourceLoaderContext( $context );
- $derivative->setModules( $this->getBaseModules() );
- $derivative->setOnly( 'scripts' );
- // Must setModules() before makeVersionQuery()
- $derivative->setVersion( $rl->makeVersionQuery( $derivative ) );
-
- return $rl->createLoaderURL( 'local', $derivative );
- }
-
/**
* @param ResourceLoaderContext $context
* @return string JavaScript code
return '/* Requires only=script */';
}
- $out = file_get_contents( "$IP/resources/src/startup/startup.js" );
+ $startupCode = file_get_contents( "$IP/resources/src/startup/startup.js" );
- // Keep in sync with maintenance/jsduck/eg-iframe.html and,
- // keep in sync with 'fileHashes' in StartUpModule::getDefinitionSummary().
+ // The files read here MUST be kept in sync with maintenance/jsduck/eg-iframe.html,
+ // and MUST be considered by 'fileHashes' in StartUpModule::getDefinitionSummary().
$mwLoaderCode = file_get_contents( "$IP/resources/src/startup/mediawiki.js" ) .
file_get_contents( "$IP/resources/src/startup/mediawiki.requestIdleCallback.js" );
if ( $context->getDebug() ) {
$mwLoaderCode .= file_get_contents( "$IP/resources/src/startup/mediawiki.log.js" );
}
+ if ( $this->getConfig()->get( 'ResourceLoaderEnableJSProfiler' ) ) {
+ $mwLoaderCode .= file_get_contents( "$IP/resources/src/startup/profiler.js" );
+ }
- $pairs = array_map( function ( $value ) {
+ $mapToJson = function ( $value ) {
$value = FormatJson::encode( $value, ResourceLoader::inDebugMode(), FormatJson::ALL_OK );
// Fix indentation
$value = str_replace( "\n", "\n\t", $value );
return $value;
- }, [
+ };
+
+ // Perform replacements for mediawiki.js
+ $mwLoaderPairs = [
+ '$VARS.baseModules' => $mapToJson( $this->getBaseModules() ),
+ ];
+ $profilerStubs = [
+ '$CODE.profileExecuteStart();' => 'mw.loader.profiler.onExecuteStart( module );',
+ '$CODE.profileExecuteEnd();' => 'mw.loader.profiler.onExecuteEnd( module );',
+ '$CODE.profileScriptStart();' => 'mw.loader.profiler.onScriptStart( module );',
+ '$CODE.profileScriptEnd();' => 'mw.loader.profiler.onScriptEnd( module );',
+ ];
+ if ( $this->getConfig()->get( 'ResourceLoaderEnableJSProfiler' ) ) {
+ // When profiling is enabled, insert the calls.
+ $mwLoaderPairs += $profilerStubs;
+ } else {
+ // When disabled (by default), insert nothing.
+ $mwLoaderPairs += array_fill_keys( array_keys( $profilerStubs ), '' );
+ }
+ $mwLoaderCode = strtr( $mwLoaderCode, $mwLoaderPairs );
+
+ // Perform replacements for startup.js
+ $pairs = array_map( $mapToJson, [
'$VARS.wgLegacyJavaScriptGlobals' => $this->getConfig()->get( 'LegacyJavaScriptGlobals' ),
'$VARS.configuration' => $this->getConfigSettings( $context ),
- // This url may be preloaded. See getPreloadLinks().
- '$VARS.baseModulesUri' => $this->getBaseModulesUrl( $context ),
] );
+ // Raw JavaScript code (not for JSON)
$pairs['$CODE.registrations();'] = str_replace(
"\n",
"\n\t",
trim( $this->getModuleRegistrations( $context ) )
);
$pairs['$CODE.defineLoader();'] = $mwLoaderCode;
+ $startupCode = strtr( $startupCode, $pairs );
- return strtr( $out, $pairs );
+ return $startupCode;
}
/**
public function getDefinitionSummary( ResourceLoaderContext $context ) {
global $IP;
$summary = parent::getDefinitionSummary( $context );
- $summary[] = [
- // Detect changes to variables exposed in mw.config (T30899).
+ $startup = [
+ // getScript() exposes these variables to mw.config (T30899).
'vars' => $this->getConfigSettings( $context ),
- // Changes how getScript() creates mw.Map for mw.config
+ // getScript() uses this to decide how configure mw.Map for mw.config.
'wgLegacyJavaScriptGlobals' => $this->getConfig()->get( 'LegacyJavaScriptGlobals' ),
- // Detect changes to the module registrations
+ // Detect changes to the module registrations output by getScript().
'moduleHashes' => $this->getAllModuleHashes( $context ),
+ // Detect changes to base modules listed by getScript().
+ 'baseModules' => $this->getBaseModules(),
'fileHashes' => [
$this->safeFileHash( "$IP/resources/src/startup/startup.js" ),
$this->safeFileHash( "$IP/resources/src/startup/mediawiki.requestIdleCallback.js" ),
],
];
+ if ( $context->getDebug() ) {
+ $startup['fileHashes'][] = $this->safeFileHash( "$IP/resources/src/startup/mediawiki.log.js" );
+ }
+ if ( $this->getConfig()->get( 'ResourceLoaderEnableJSProfiler' ) ) {
+ $startup['fileHashes'][] = $this->safeFileHash( "$IP/resources/src/startup/profiling.js" );
+ }
+ $summary[] = $startup;
return $summary;
}