MediaWiki REL1_38
Setup.php
Go to the documentation of this file.
1<?php
53// phpcs:disable MediaWiki.Usage.DeprecatedGlobalVariables
63use Psr\Log\LoggerInterface;
64use Wikimedia\AtEase\AtEase;
65use Wikimedia\RequestTimeout\RequestTimeout;
66
74// This file must be included from a valid entry point (e.g. WebStart.php, Maintenance.php)
75if ( !defined( 'MEDIAWIKI' ) ) {
76 exit( 1 );
77}
78
79// PHP must not be configured to overload mbstring functions. (T5782, T122807)
80// This was deprecated by upstream in PHP 7.2, likely to be removed in PHP 8.0.
81if ( ini_get( 'mbstring.func_overload' ) ) {
82 die( 'MediaWiki does not support installations where mbstring.func_overload is non-zero.' );
83}
84
85// The MW_ENTRY_POINT constant must always exists, to make it safe to access.
86// For compat, we do support older and custom MW entrypoints that don't set this,
87// in which case we assign a default here.
88if ( !defined( 'MW_ENTRY_POINT' ) ) {
94 define( 'MW_ENTRY_POINT', 'unknown' );
95}
96
97if ( !defined( 'MW_INSTALL_PATH' ) ) {
98 define( 'MW_INSTALL_PATH', $IP );
99} else {
100 // enforce consistency
101 $IP = MW_INSTALL_PATH;
102}
103
109require_once "$IP/includes/AutoLoader.php";
110require_once "$IP/includes/Defines.php";
111require_once "$IP/includes/BootstrapHelperFunctions.php";
112
113// Load composer's autoloader if present
114if ( is_readable( "$IP/vendor/autoload.php" ) ) {
115 require_once "$IP/vendor/autoload.php";
116} elseif ( file_exists( "$IP/vendor/autoload.php" ) ) {
117 die( "$IP/vendor/autoload.php exists but is not readable" );
118}
119
120// Assert that composer dependencies were successfully loaded
121if ( !interface_exists( LoggerInterface::class ) ) {
122 $message = (
123 'MediaWiki requires the <a href="https://github.com/php-fig/log">PSR-3 logging ' .
124 "library</a> to be present. This library is not embedded directly in MediaWiki's " .
125 "git repository and must be installed separately by the end user.\n\n" .
126 'Please see the <a href="https://www.mediawiki.org/wiki/Download_from_Git' .
127 '#Fetch_external_libraries">instructions for installing libraries</a> on mediawiki.org ' .
128 'for help on installing the required components.'
129 );
130 echo $message;
131 trigger_error( $message, E_USER_ERROR );
132}
133
134// explicitly global, so it works with wfRequireOnceInGlobalScope()
136
137// Set $wgCommandLineMode to false if it wasn't set to true.
139
146
148
150 $IP,
151 ExtensionRegistry::getInstance(),
152 new GlobalConfigBuilder( 'wg' ),
153 new PhpIniSink()
154);
155
156if ( getenv( 'MW_USE_LEGACY_DEFAULT_SETTINGS' ) || defined( 'MW_USE_LEGACY_DEFAULT_SETTINGS' ) ) {
157 // Load the old DefaultSettings.php file. Should be removed in 1.39. See T300129.
158 require_once "$IP/includes/DefaultSettings.php";
159
160 // This is temporary until we no longer need this mode.
161 $wgSettings->load( new PhpSettingsSource( "$IP/includes/config-merge-strategies.php" ) );
162} else {
163 $wgSettings->load( new PhpSettingsSource( "$IP/includes/config-schema.php" ) );
164}
165
166require_once "$IP/includes/GlobalFunctions.php";
167
168HeaderCallback::register();
169
170// Set the encoding used by PHP for reading HTTP input, and writing output.
171// This is also the default for mbstring functions.
172mb_internal_encoding( 'UTF-8' );
173
178// Initialize some config settings with dynamic defaults, and
179// make default settings available in globals for use in LocalSettings.php.
180$wgSettings->putConfigValues( [
181 'BaseDirectory' => $IP,
182 'ExtensionDirectory' => "{$IP}/extensions",
183 'StyleDirectory' => "{$IP}/skins",
184 'ServiceWiringFiles' => [ "{$IP}/includes/ServiceWiring.php" ],
185 'Version' => MW_VERSION,
186] );
187$wgSettings->apply();
188
189if ( defined( 'MW_CONFIG_CALLBACK' ) ) {
190 call_user_func( MW_CONFIG_CALLBACK, $wgSettings );
191} else {
193
194 if ( getenv( 'MW_USE_LOCAL_SETTINGS_LOADER' ) ) {
195 // NOTE: This will not work for configuration variables that use a prefix
196 // other than "wg".
197 $localSettingsLoader = new LocalSettingsLoader( $wgSettings, $IP );
198 $localSettingsLoader->loadLocalSettingsFile( MW_CONFIG_FILE );
199 unset( $localSettingsLoader );
200 } else {
201 if ( str_ends_with( MW_CONFIG_FILE, '.php' ) ) {
202 // make defaults available as globals
203 $wgSettings->apply();
204 require_once MW_CONFIG_FILE;
205 } else {
206 $wgSettings->loadFile( MW_CONFIG_FILE );
207 }
208 }
209}
210
211// Make settings loaded by LocalSettings.php available in globals for use here
212$wgSettings->apply();
213
221if ( defined( 'MW_SETUP_CALLBACK' ) ) {
222 call_user_func( MW_SETUP_CALLBACK, $wgSettings );
223 // Make any additional settings available in globals for use here
224 $wgSettings->apply();
225}
226
227// If in a wiki-farm, load site-specific settings
228if ( $wgSettings->getConfig()->get( 'WikiFarmSettingsDirectory' ) ) {
229 $wikiFarmSettingsLoader = new WikiFarmSettingsLoader( $wgSettings );
230 $wikiFarmSettingsLoader->loadWikiFarmSettings();
231 unset( $wikiFarmSettingsLoader );
232}
233
234// All settings should be loaded now.
235$wgSettings->finalize();
236if ( $wgBaseDirectory !== MW_INSTALL_PATH ) {
237 throw new FatalError(
238 '$wgBaseDirectory must not be modified in settings files! ' .
239 'Use the MW_INSTALL_PATH environment variable to override the installation root directory.'
240 );
241}
242
243// Start time limit
245 RequestTimeout::singleton()->setWallTimeLimit( $wgRequestTimeLimit );
246}
247
252ExtensionRegistry::getInstance()->loadFromQueue();
253// Don't let any other extensions load
255
256// Set an appropriate locale (T291234)
257// setlocale() will return the locale name actually set.
258// The putenv() is meant to propagate the choice of locale to shell commands
259// so that they will interpret UTF-8 correctly. If you have a problem with a
260// shell command and need to send a special locale, you can override the locale
261// with Command::environment().
262putenv( "LC_ALL=" . setlocale( LC_ALL, 'C.UTF-8', 'C' ) );
263
268if ( $wgScript === false ) {
269 $wgScript = "$wgScriptPath/index.php";
270}
271if ( $wgLoadScript === false ) {
272 $wgLoadScript = "$wgScriptPath/load.php";
273}
274if ( $wgRestPath === false ) {
275 $wgRestPath = "$wgScriptPath/rest.php";
276}
277if ( $wgUsePathInfo === null ) {
278 // These often break when PHP is set up in CGI mode.
279 // PATH_INFO *may* be correct if cgi.fix_pathinfo is set, but then again it may not;
280 // lighttpd converts incoming path data to lowercase on systems
281 // with case-insensitive filesystems, and there have been reports of
282 // problems on Apache as well.
283 $wgUsePathInfo = ( strpos( PHP_SAPI, 'cgi' ) === false ) &&
284 ( strpos( PHP_SAPI, 'apache2filter' ) === false ) &&
285 ( strpos( PHP_SAPI, 'isapi' ) === false );
286}
287if ( $wgArticlePath === false ) {
288 if ( $wgUsePathInfo ) {
289 $wgArticlePath = "$wgScript/$1";
290 } else {
291 $wgArticlePath = "$wgScript?title=$1";
292 }
293}
294if ( $wgResourceBasePath === null ) {
296}
297if ( $wgStylePath === false ) {
298 $wgStylePath = "$wgResourceBasePath/skins";
299}
300if ( $wgLocalStylePath === false ) {
301 // Avoid wgResourceBasePath here since that may point to a different domain (e.g. CDN)
302 $wgLocalStylePath = "$wgScriptPath/skins";
303}
304if ( $wgExtensionAssetsPath === false ) {
305 $wgExtensionAssetsPath = "$wgResourceBasePath/extensions";
306}
307
308// For backwards compatibility, the value of wgLogos is copied to wgLogo.
309// This is because some extensions/skins may be using $config->get('Logo')
310// to access the value.
311if ( $wgLogos !== false && isset( $wgLogos['1x'] ) ) {
312 $wgLogo = $wgLogos['1x'];
313}
314if ( $wgLogo === false ) {
315 $wgLogo = "$wgResourceBasePath/resources/assets/change-your-logo.svg";
316}
317
318if ( $wgUploadPath === false ) {
319 $wgUploadPath = "$wgScriptPath/images";
320}
321if ( $wgUploadDirectory === false ) {
322 $wgUploadDirectory = "$IP/images";
323}
324if ( $wgReadOnlyFile === false ) {
325 $wgReadOnlyFile = "{$wgUploadDirectory}/lock_yBgMBwiR";
326}
327if ( $wgFileCacheDirectory === false ) {
328 $wgFileCacheDirectory = "{$wgUploadDirectory}/cache";
329}
330if ( $wgDeletedDirectory === false ) {
331 $wgDeletedDirectory = "{$wgUploadDirectory}/deleted";
332}
333if ( $wgGitInfoCacheDirectory === false && $wgCacheDirectory !== false ) {
334 $wgGitInfoCacheDirectory = "{$wgCacheDirectory}/gitinfo";
335}
336if ( $wgSharedPrefix === false ) {
338}
339if ( $wgSharedSchema === false ) {
341}
342if ( $wgMetaNamespace === false ) {
343 $wgMetaNamespace = str_replace( ' ', '_', $wgSitename );
344}
345
346if ( $wgMainWANCache === false ) {
347 // Create a WAN cache from $wgMainCacheType
348 $wgMainWANCache = 'mediawiki-main-default';
350 'class' => WANObjectCache::class,
351 'cacheId' => $wgMainCacheType,
352 ];
353}
354
355// Back-compat
356if ( isset( $wgFileBlacklist ) ) {
357 $wgProhibitedFileExtensions = array_merge( $wgProhibitedFileExtensions, $wgFileBlacklist );
358} else {
359 $wgFileBlacklist = $wgProhibitedFileExtensions;
360}
361if ( isset( $wgMimeTypeBlacklist ) ) {
362 $wgMimeTypeExclusions = array_merge( $wgMimeTypeExclusions, $wgMimeTypeBlacklist );
363} else {
364 $wgMimeTypeBlacklist = $wgMimeTypeExclusions;
365}
366if ( isset( $wgEnableUserEmailBlacklist ) ) {
367 $wgEnableUserEmailMuteList = $wgEnableUserEmailBlacklist;
368} else {
369 $wgEnableUserEmailBlacklist = $wgEnableUserEmailMuteList;
370}
371if ( isset( $wgShortPagesNamespaceBlacklist ) ) {
372 $wgShortPagesNamespaceExclusions = $wgShortPagesNamespaceBlacklist;
373} else {
374 $wgShortPagesNamespaceBlacklist = $wgShortPagesNamespaceExclusions;
375}
376
377// Prohibited file extensions shouldn't appear on the "allowed" list
379
380// Fix path to icon images after they were moved in 1.24
381if ( $wgRightsIcon ) {
382 $wgRightsIcon = str_replace(
383 "{$wgStylePath}/common/images/",
384 "{$wgResourceBasePath}/resources/assets/licenses/",
386 );
387}
388
389if ( isset( $wgFooterIcons['copyright']['copyright'] )
390 && $wgFooterIcons['copyright']['copyright'] === []
391) {
392 if ( $wgRightsIcon || $wgRightsText ) {
393 $wgFooterIcons['copyright']['copyright'] = [
394 'url' => $wgRightsUrl,
395 'src' => $wgRightsIcon,
396 'alt' => $wgRightsText,
397 ];
398 }
399}
400
401if ( isset( $wgFooterIcons['poweredby'] )
402 && isset( $wgFooterIcons['poweredby']['mediawiki'] )
403 && $wgFooterIcons['poweredby']['mediawiki']['src'] === null
404) {
405 $wgFooterIcons['poweredby']['mediawiki']['src'] =
406 "$wgResourceBasePath/resources/assets/poweredby_mediawiki_88x31.png";
407 $wgFooterIcons['poweredby']['mediawiki']['srcset'] =
408 "$wgResourceBasePath/resources/assets/poweredby_mediawiki_132x47.png 1.5x, " .
409 "$wgResourceBasePath/resources/assets/poweredby_mediawiki_176x62.png 2x";
410}
411
420
425 'name' => 'fsLockManager',
426 'class' => FSLockManager::class,
427 'lockDirectory' => "{$wgUploadDirectory}/lockdir",
428];
429$wgLockManagers[] = [
430 'name' => 'nullLockManager',
431 'class' => NullLockManager::class,
432];
433
437if ( $wgShowEXIF === null ) {
438 $wgShowEXIF = function_exists( 'exif_read_data' );
439}
440
446 'imagesPerRow' => 0,
447 'imageWidth' => 120,
448 'imageHeight' => 120,
449 'captionLength' => true,
450 'showBytes' => true,
451 'showDimensions' => true,
452 'mode' => 'traditional',
453];
454
458if ( !$wgLocalFileRepo ) {
460 'class' => LocalRepo::class,
461 'name' => 'local',
462 'directory' => $wgUploadDirectory,
463 'scriptDirUrl' => $wgScriptPath,
464 'favicon' => $wgFavicon,
466 'hashLevels' => $wgHashedUploadDirectory ? 2 : 0,
467 'thumbScriptUrl' => $wgThumbnailScriptPath,
468 'transformVia404' => !$wgGenerateThumbnailOnParse,
469 'deletedDir' => $wgDeletedDirectory,
470 'deletedHashLevels' => $wgHashedUploadDirectory ? 3 : 0,
471 'updateCompatibleMetadata' => $wgUpdateCompatibleMetadata,
472 'reserializeMetadata' => $wgUpdateCompatibleMetadata,
473 ];
474}
475
476if ( !isset( $wgLocalFileRepo['backend'] ) ) {
477 // Create a default FileBackend name.
478 // FileBackendGroup will register a default, if absent from $wgFileBackends.
479 $wgLocalFileRepo['backend'] = $wgLocalFileRepo['name'] . '-backend';
480}
481
485if ( $wgUseSharedUploads ) {
486 if ( $wgSharedUploadDBname ) {
488 'class' => ForeignDBRepo::class,
489 'name' => 'shared',
490 'directory' => $wgSharedUploadDirectory,
491 'url' => $wgSharedUploadPath,
492 'hashLevels' => $wgHashedSharedUploadDirectory ? 2 : 0,
493 'thumbScriptUrl' => $wgSharedThumbnailScriptPath,
494 'transformVia404' => !$wgGenerateThumbnailOnParse,
495 'dbType' => $wgDBtype,
496 'dbServer' => $wgDBserver,
497 'dbUser' => $wgDBuser,
498 'dbPassword' => $wgDBpassword,
499 'dbName' => $wgSharedUploadDBname,
500 'dbFlags' => ( $wgDebugDumpSql ? DBO_DEBUG : 0 ) | DBO_DEFAULT,
501 'tablePrefix' => $wgSharedUploadDBprefix,
502 'hasSharedCache' => $wgCacheSharedUploads,
503 'descBaseUrl' => $wgRepositoryBaseUrl,
504 'fetchDescription' => $wgFetchCommonsDescriptions,
505 ];
506 } else {
508 'class' => FileRepo::class,
509 'name' => 'shared',
510 'directory' => $wgSharedUploadDirectory,
511 'url' => $wgSharedUploadPath,
512 'hashLevels' => $wgHashedSharedUploadDirectory ? 2 : 0,
513 'thumbScriptUrl' => $wgSharedThumbnailScriptPath,
514 'transformVia404' => !$wgGenerateThumbnailOnParse,
515 'descBaseUrl' => $wgRepositoryBaseUrl,
516 'fetchDescription' => $wgFetchCommonsDescriptions,
517 ];
518 }
519}
522 'class' => ForeignAPIRepo::class,
523 'name' => 'wikimediacommons',
524 'apibase' => 'https://commons.wikimedia.org/w/api.php',
525 'url' => 'https://upload.wikimedia.org/wikipedia/commons',
526 'thumbUrl' => 'https://upload.wikimedia.org/wikipedia/commons/thumb',
527 'hashLevels' => 2,
528 'transformVia404' => true,
529 'fetchDescription' => true,
530 'descriptionCacheExpiry' => 43200,
531 'apiThumbCacheExpiry' => 0,
532 ];
533}
534foreach ( $wgForeignFileRepos as &$repo ) {
535 if ( !isset( $repo['directory'] ) && $repo['class'] === ForeignAPIRepo::class ) {
536 $repo['directory'] = $wgUploadDirectory; // b/c
537 }
538 if ( !isset( $repo['backend'] ) ) {
539 $repo['backend'] = $repo['name'] . '-backend';
540 }
541}
542unset( $repo ); // no global pollution; destroy reference
543
544$rcMaxAgeDays = $wgRCMaxAge / ( 3600 * 24 );
545// Ensure that default user options are not invalid, since that breaks Special:Preferences
546$wgDefaultUserOptions['rcdays'] = min(
547 $wgDefaultUserOptions['rcdays'],
548 ceil( $rcMaxAgeDays )
549);
550$wgDefaultUserOptions['watchlistdays'] = min(
551 $wgDefaultUserOptions['watchlistdays'],
552 ceil( $rcMaxAgeDays )
553);
554unset( $rcMaxAgeDays );
555
556if ( !$wgCookiePrefix ) {
557 if ( $wgSharedDB && $wgSharedPrefix && in_array( 'user', $wgSharedTables ) ) {
559 } elseif ( $wgSharedDB && in_array( 'user', $wgSharedTables ) ) {
561 } elseif ( $wgDBprefix ) {
563 } else {
565 }
566}
567$wgCookiePrefix = strtr( $wgCookiePrefix, '=,; +."\'\\[', '__________' );
568
569if ( $wgEnableEmail ) {
571} else {
572 // Disable all other email settings automatically if $wgEnableEmail
573 // is set to false. - T65678
574 $wgAllowHTMLEmail = false;
575 $wgEmailAuthentication = false; // do not require auth if you're not sending email anyway
585 unset( $wgGroupPermissions['user']['sendemail'] );
589}
590
591if ( $wgLocaltimezone === null ) {
592 // This defaults to the `date.timezone` value of the PHP INI option. If this option is not set,
593 // it falls back to UTC. Prior to PHP 7.0, this fallback produced a warning.
594 $wgLocaltimezone = date_default_timezone_get();
595}
596date_default_timezone_set( $wgLocaltimezone );
597if ( $wgLocalTZoffset === null ) {
598 $wgLocalTZoffset = (int)date( 'Z' ) / 60;
599}
600// The part after the System| is ignored, but rest of MW fills it out as the local offset.
601$wgDefaultUserOptions['timecorrection'] = "System|$wgLocalTZoffset";
602
603if ( !$wgDBerrorLogTZ ) {
605}
606
611$wgCanonicalNamespaceNames = NamespaceInfo::CANONICAL_NAMES;
612
613// @todo UGLY UGLY
614if ( is_array( $wgExtraNamespaces ) ) {
616}
617
618// Hard-deprecate setting $wgDummyLanguageCodes in LocalSettings.php
619if ( count( $wgDummyLanguageCodes ) !== 0 ) {
620 wfDeprecated( '$wgDummyLanguageCodes', '1.29' );
621}
622// Merge in the legacy language codes, incorporating overrides from the config
624 // Internal language codes of the private-use area which get mapped to
625 // themselves.
626 'qqq' => 'qqq', // Used for message documentation
627 'qqx' => 'qqx', // Used for viewing message keys
628] + $wgExtraLanguageCodes + LanguageCode::getDeprecatedCodeMapping();
629// Merge in (inverted) BCP 47 mappings
630foreach ( LanguageCode::getNonstandardLanguageCodeMapping() as $code => $bcp47 ) {
631 $bcp47 = strtolower( $bcp47 ); // force case-insensitivity
632 if ( !isset( $wgDummyLanguageCodes[$bcp47] ) ) {
633 $wgDummyLanguageCodes[$bcp47] = $wgDummyLanguageCodes[$code] ?? $code;
634 }
635}
636unset( $code ); // no global pollution; destroy reference
637unset( $bcp47 ); // no global pollution; destroy reference
638
639// Temporary backwards-compatibility reading of old replica lag settings as of MediaWiki 1.36,
640// to support sysadmins who fail to update their settings immediately:
641
642if ( isset( $wgSlaveLagWarning ) ) {
643 // If the old value is set to something other than the default, use it.
644 if ( $wgDatabaseReplicaLagWarning === 10 && $wgSlaveLagWarning !== 10 ) {
645 $wgDatabaseReplicaLagWarning = $wgSlaveLagWarning;
647 '$wgSlaveLagWarning set but $wgDatabaseReplicaLagWarning unchanged; using $wgSlaveLagWarning',
648 '1.36'
649 );
650 }
651} else {
652 // Backwards-compatibility for extensions that read this value.
653 $wgSlaveLagWarning = $wgDatabaseReplicaLagWarning;
654}
655
656if ( isset( $wgSlaveLagCritical ) ) {
657 // If the old value is set to something other than the default, use it.
658 if ( $wgDatabaseReplicaLagCritical === 30 && $wgSlaveLagCritical !== 30 ) {
659 $wgDatabaseReplicaLagCritical = $wgSlaveLagCritical;
661 '$wgSlaveLagCritical set but $wgDatabaseReplicaLagCritical unchanged; using $wgSlaveLagCritical',
662 '1.36'
663 );
664 }
665} else {
666 // Backwards-compatibility for extensions that read this value.
667 $wgSlaveLagCritical = $wgDatabaseReplicaLagCritical;
668}
669
670if ( $wgInvalidateCacheOnLocalSettingsChange && defined( 'MW_CONFIG_FILE' ) ) {
671 AtEase::suppressWarnings();
672 $wgCacheEpoch = max( $wgCacheEpoch, gmdate( 'YmdHis', filemtime( MW_CONFIG_FILE ) ) );
673 AtEase::restoreWarnings();
674}
675
676if ( $wgNewUserLog ) {
677 // Add new user log type
678 $wgLogTypes[] = 'newusers';
679 $wgLogNames['newusers'] = 'newuserlogpage';
680 $wgLogHeaders['newusers'] = 'newuserlogpagetext';
681 $wgLogActionsHandlers['newusers/newusers'] = NewUsersLogFormatter::class;
682 $wgLogActionsHandlers['newusers/create'] = NewUsersLogFormatter::class;
683 $wgLogActionsHandlers['newusers/create2'] = NewUsersLogFormatter::class;
684 $wgLogActionsHandlers['newusers/byemail'] = NewUsersLogFormatter::class;
685 $wgLogActionsHandlers['newusers/autocreate'] = NewUsersLogFormatter::class;
686}
687
688if ( $wgPageCreationLog ) {
689 // Add page creation log type
690 $wgLogTypes[] = 'create';
691 $wgLogActionsHandlers['create/create'] = LogFormatter::class;
692}
693
695 $wgLogTypes[] = 'pagelang';
696 $wgLogActionsHandlers['pagelang/pagelang'] = PageLangLogFormatter::class;
697}
698
699if ( $wgCookieSecure === 'detect' ) {
701}
702
703// Backwards compatibility with old password limits
704if ( $wgMinimalPasswordLength !== false ) {
705 $wgPasswordPolicy['policies']['default']['MinimalPasswordLength'] = $wgMinimalPasswordLength;
706}
707
708if ( $wgMaximalPasswordLength !== false ) {
709 $wgPasswordPolicy['policies']['default']['MaximalPasswordLength'] = $wgMaximalPasswordLength;
710}
711
712if ( $wgPHPSessionHandling !== 'enable' &&
713 $wgPHPSessionHandling !== 'warn' &&
714 $wgPHPSessionHandling !== 'disable'
715) {
716 $wgPHPSessionHandling = 'warn';
717}
718if ( defined( 'MW_NO_SESSION' ) ) {
719 // If the entry point wants no session, force 'disable' here unless they
720 // specifically set it to the (undocumented) 'warn'.
721 $wgPHPSessionHandling = MW_NO_SESSION === 'warn' ? 'warn' : 'disable';
722}
723
725
726// Enable the global service locator.
727// Trivial expansion of site configuration should go before this point.
728// Any non-trivial expansion that requires calling into MediaWikiServices or other parts of MW.
729MediaWikiServices::allowGlobalInstance();
730
731// Define a constant that indicates that the bootstrapping of the service locator
732// is complete.
733define( 'MW_SERVICE_BOOTSTRAP_COMPLETE', 1 );
734
735MWExceptionHandler::installHandler();
736
737// Non-trivial validation of: $wgServer
738// The FatalError page only renders cleanly after MWExceptionHandler is installed.
739if ( $wgServer === false ) {
740 // T30798: $wgServer must be explicitly set
741 throw new FatalError(
742 '$wgServer must be set in LocalSettings.php. ' .
743 'See <a href="https://www.mediawiki.org/wiki/Manual:$wgServer">' .
744 'https://www.mediawiki.org/wiki/Manual:$wgServer</a>.'
745 );
746}
747
748// Non-trivial expansion of: $wgCanonicalServer, $wgServerName.
749// These require calling global functions.
750// Also here are other settings that further depend on these two.
751if ( $wgCanonicalServer === false ) {
753}
755
757if ( $wgServerName !== false ) {
758 wfWarn( '$wgServerName should be derived from $wgCanonicalServer, '
759 . 'not customized. Overwriting $wgServerName.' );
760}
762unset( $serverParts );
763
764// $wgEmergencyContact and $wgPasswordSender may be false or empty string (T104142)
765if ( !$wgEmergencyContact ) {
766 $wgEmergencyContact = 'wikiadmin@' . $wgServerName;
767}
768if ( !$wgPasswordSender ) {
769 $wgPasswordSender = 'apache@' . $wgServerName;
770}
771if ( !$wgNoReplyAddress ) {
773}
774
775// Non-trivial expansion of: $wgSecureLogin
776// (due to calling wfWarn).
777if ( $wgSecureLogin && substr( $wgServer, 0, 2 ) !== '//' ) {
778 $wgSecureLogin = false;
779 wfWarn( 'Secure login was enabled on a server that only supports '
780 . 'HTTP or HTTPS. Disabling secure login.' );
781}
782
783// Now that GlobalFunctions is loaded, set defaults that depend on it.
784if ( $wgTmpDirectory === false ) {
786}
787
789 // Apply $wgSharedDB table aliases for the local LB (all non-foreign DB connections)
790 MediaWikiServices::getInstance()->getDBLoadBalancer()->setTableAliases(
791 array_fill_keys(
793 [
794 'dbname' => $wgSharedDB,
795 'schema' => $wgSharedSchema,
796 'prefix' => $wgSharedPrefix
797 ]
798 )
799 );
800}
801
802// Raise the memory limit if it's too low
803// NOTE: This use wfDebug, and must remain after the MWDebug::setup() call.
805
806// Explicit globals, so this works with bootstrap.php
808
809// Initialize the request object in $wgRequest
810$wgRequest = RequestContext::getMain()->getRequest(); // BackCompat
811
812// Make sure that object caching does not undermine the ChronologyProtector improvements
813if ( $wgRequest->getCookie( 'UseDC', '' ) === 'master' ) {
814 // The user is pinned to the primary DC, meaning that they made recent changes which should
815 // be reflected in their subsequent web requests. Avoid the use of interim cache keys because
816 // they use a blind TTL and could be stale if an object changes twice in a short time span.
817 MediaWikiServices::getInstance()->getMainWANObjectCache()->useInterimHoldOffCaching( false );
818}
819
820// Useful debug output
821( static function () {
823 $logger = LoggerFactory::getInstance( 'wfDebug' );
824 if ( $wgCommandLineMode ) {
825 $self = $_SERVER['PHP_SELF'] ?? '';
826 $logger->debug( "\n\nStart command line script $self" );
827 } else {
828 $debug = "\n\nStart request {$wgRequest->getMethod()} {$wgRequest->getRequestURL()}\n";
829 $debug .= "IP: " . $wgRequest->getIP() . "\n";
830 $debug .= "HTTP HEADERS:\n";
831 foreach ( $wgRequest->getAllHeaders() as $name => $value ) {
832 $debug .= "$name: $value\n";
833 }
834 $debug .= "(end headers)";
835 $logger->debug( $debug );
836 }
837} )();
838
839// Most of the config is out, some might want to run hooks here.
840Hooks::runner()->onSetupAfterCache();
841
842// Now that variant lists may be available, parse any action paths and article paths
843// as query parameters.
844//
845// Skip title interpolation on API queries where it is useless and sometimes harmful (T18019).
846//
847// Optimization: Skip on load.php and all other entrypoints besides index.php to save time.
848//
849// TODO: Figure out if this can be safely done after everything else in Setup.php (e.g. any
850// hooks or other state that would miss this?). If so, move to wfIndexMain or MediaWiki::run.
851if ( MW_ENTRY_POINT === 'index' ) {
852 $wgRequest->interpolateTitle();
853}
854
859if ( !defined( 'MW_NO_SESSION' ) && !$wgCommandLineMode ) {
860 // If session.auto_start is there, we can't touch session name
861 if ( $wgPHPSessionHandling !== 'disable' && !wfIniGetBool( 'session.auto_start' ) ) {
862 HeaderCallback::warnIfHeadersSent();
863 session_name( $wgSessionName ?: $wgCookiePrefix . '_session' );
864 }
865
866 // Create the SessionManager singleton and set up our session handler,
867 // unless we're specifically asked not to.
868 if ( !defined( 'MW_NO_SESSION_HANDLER' ) ) {
869 MediaWiki\Session\PHPSessionHandler::install(
870 MediaWiki\Session\SessionManager::singleton()
871 );
872 }
873
874 $contLang = MediaWikiServices::getInstance()->getContentLanguage();
875
876 // Initialize the session
877 try {
878 $session = MediaWiki\Session\SessionManager::getGlobalSession();
879 } catch ( MediaWiki\Session\SessionOverflowException $ex ) {
880 // The exception is because the request had multiple possible
881 // sessions tied for top priority. Report this to the user.
882 $list = [];
883 foreach ( $ex->getSessionInfos() as $info ) {
884 $list[] = $info->getProvider()->describe( $contLang );
885 }
886 $list = $contLang->listToText( $list );
887 throw new HttpError( 400,
888 Message::newFromKey( 'sessionmanager-tie', $list )->inLanguage( $contLang )
889 );
890 }
891
892 unset( $contLang );
893
894 if ( $session->isPersistent() ) {
895 $wgInitialSessionId = $session->getSessionId();
896 }
897
898 $session->renew();
899 if ( MediaWiki\Session\PHPSessionHandler::isEnabled() &&
900 ( $session->isPersistent() || $session->shouldRememberUser() ) &&
901 session_id() !== $session->getId()
902 ) {
903 // Start the PHP-session for backwards compatibility
904 if ( session_id() !== '' ) {
905 wfDebugLog( 'session', 'PHP session {old_id} was already started, changing to {new_id}', 'all', [
906 'old_id' => session_id(),
907 'new_id' => $session->getId(),
908 ] );
909 session_write_close();
910 }
911 session_id( $session->getId() );
912 session_start();
913 }
914
915 unset( $session );
916} else {
917 // Even if we didn't set up a global Session, still install our session
918 // handler unless specifically requested not to.
919 if ( !defined( 'MW_NO_SESSION_HANDLER' ) ) {
920 MediaWiki\Session\PHPSessionHandler::install(
921 MediaWiki\Session\SessionManager::singleton()
922 );
923 }
924}
925
926// Explicit globals, so this works with bootstrap.php
928
934$wgUser = new StubGlobalUser( RequestContext::getMain()->getUser() ); // BackCompat
935register_shutdown_function( static function () {
937} );
938
943
947$wgOut = RequestContext::getMain()->getOutput(); // BackCompat
948
953$wgParser = new DeprecatedGlobal( 'wgParser', static function () {
954 return MediaWikiServices::getInstance()->getParser();
955}, '1.32' );
956
960$wgTitle = null;
961
962// Explicit globals, so this works with bootstrap.php
964
965// Extension setup functions
966// Entries should be added to this variable during the inclusion
967// of the extension file. This allows the extension to perform
968// any necessary initialisation in the fully initialised environment
969foreach ( $wgExtensionFunctions as $func ) {
970 call_user_func( $func );
971}
972unset( $func ); // no global pollution; destroy reference
973
974// If the session user has a 0 id but a valid name, that means we need to
975// autocreate it.
976if ( !defined( 'MW_NO_SESSION' ) && !$wgCommandLineMode ) {
977 $sessionUser = MediaWiki\Session\SessionManager::getGlobalSession()->getUser();
978 if ( $sessionUser->getId() === 0 &&
979 MediaWikiServices::getInstance()->getUserNameUtils()->isValid( $sessionUser->getName() )
980 ) {
981 $res = MediaWikiServices::getInstance()->getAuthManager()->autoCreateUser(
982 $sessionUser,
983 MediaWiki\Auth\AuthManager::AUTOCREATE_SOURCE_SESSION,
984 true
985 );
986 \MediaWiki\Logger\LoggerFactory::getInstance( 'authevents' )->info( 'Autocreation attempt', [
987 'event' => 'autocreate',
988 'status' => strval( $res ),
989 ] );
990 unset( $res );
991 }
992 unset( $sessionUser );
993}
994
995if ( !$wgCommandLineMode ) {
997}
998
1000
1001// T264370
1002if ( !defined( 'MW_NO_SESSION' ) && !$wgCommandLineMode ) {
1003 MediaWiki\Session\SessionManager::singleton()->logPotentialSessionLeakage();
1004}
getUser()
wfDetectLocalSettingsFile(string $installationPath)
Decide and remember where to load LocalSettings from.
$wgProhibitedFileExtensions
Files with these extensions will never be allowed as uploads.
$wgRightsIcon
Override for copyright metadata.
$wgCacheEpoch
Set this to current time to invalidate all prior cached pages.
bool $wgPageLanguageUseDB
Enable page language feature Allows setting page language in database.
string $wgSharedUploadDirectory
Shortcut for the 'directory' setting of $wgForeignFileRepos.
$wgUsePathInfo
Whether to support URLs like index.php/Page_title These often break when PHP is set up in CGI mode.
$wgMemoryLimit
The minimum amount of memory that MediaWiki "needs"; MediaWiki will try to raise PHP's memory limit i...
$wgEmergencyContact
Site admin email address.
$wgDBprefix
Current wiki database table name prefix.
$wgDBuser
Database username.
$wgUpdateCompatibleMetadata
Shortcut for the 'updateCompatibleMetadata' setting of $wgLocalFileRepo.
string $wgPHPSessionHandling
Whether to use PHP session handling ($_SESSION and session_*() functions)
bool $wgCacheSharedUploads
Shortcut for the ForeignDBRepo 'hasSharedCache' setting in $wgForeignFileRepos.
bool string $wgSharedUploadDBname
Shortcut for the ForeignDBRepo 'dbName' setting in $wgForeignFileRepos.
$wgScript
The URL path to index.php.
$wgUseInstantCommons
Use Wikimedia Commons as a foreign file repository.
$wgEnableUserEmailMuteList
Set to true to enable user-to-user e-mail mutelist.
bool $wgHashedSharedUploadDirectory
Shortcut for the 'hashLevels' setting of $wgForeignFileRepos.
$wgCacheDirectory
Directory for caching data in the local filesystem.
$wgRightsUrl
Set this to specify an external URL containing details about the content license used on your wiki.
$wgSharedTables
$wgSessionName
Override to customise the session name.
$wgMainCacheType
Main cache type.
$wgPasswordPolicy
Password policy for the wiki.
$wgLogNames
Lists the message key string for each log type.
$wgInvalidateCacheOnLocalSettingsChange
Invalidate various caches when LocalSettings.php changes.
$wgLocalStylePath
The URL path of the skins directory.
$wgThumbnailScriptPath
Give a path here to use thumb.php for thumbnail generation on client request, instead of generating t...
$wgExtraNamespaces
Additional namespaces.
$wgTmpDirectory
The local filesystem path to a temporary directory.
bool $wgGenerateThumbnailOnParse
Render thumbnails while parsing wikitext.
bool $wgUseSharedUploads
Shortcut for adding an entry to $wgForeignFileRepos.
string $wgSharedUploadDBprefix
Shortcut for the ForeignDBRepo 'tablePrefix' setting in $wgForeignFileRepos.
$wgDBtype
Database type.
$wgDBmwschema
Current wiki database schema name.
$wgNoReplyAddress
Reply-To address for e-mail notifications.
$wgDBname
Current wiki database name.
$wgDBerrorLogTZ
Timezone to use in the error log.
$wgUploadDirectory
The filesystem path of the images directory.
$wgLogTypes
The logging system has two levels: an event type, which describes the general category and can be vie...
$wgMaximalPasswordLength
Specifies the maximal length of a user password (T64685).
$wgSitename
Name of the site.
$wgShortPagesNamespaceExclusions
Optional array of namespaces which should be excluded from Special:ShortPages.
$wgReadOnlyFile
If this lock file exists (size > 0), the wiki will be forced into read-only mode.
$wgFileCacheDirectory
Directory where the cached page will be saved.
$wgRightsText
If either $wgRightsUrl or $wgRightsPage is specified then this variable gives the text for the link.
$wgGitInfoCacheDirectory
Directory where GitInfo will look for pre-computed cache files.
$wgPageCreationLog
Maintain a log of page creations at Special:Log/create?
$wgDatabaseReplicaLagCritical
$wgResourceBasePath
The default 'remoteBasePath' value for instances of ResourceLoaderFileModule.
$wgFooterIcons
Abstract list of footer icons for skins in place of old copyrightico and poweredbyico code You can ad...
$wgArticlePath
The URL path for primary article page views.
$wgUploadPath
The URL path for the images directory.
$wgEnableEmail
Set to true to enable the e-mail basic features: Password reminders, etc.
$wgBaseDirectory
Absolute filesystem path of the root directory of the MediaWiki installation.
$wgSecureLogin
This is to let user authenticate using https when they come from http.
$wgRCMaxAge
Recentchanges items are periodically purged; entries older than this many seconds will go.
bool $wgHashedUploadDirectory
Shortcut for setting hashLevels=2 in $wgLocalFileRepo.
$wgLocaltimezone
Fake out the timezone that the server thinks it's in.
$wgUploadBaseUrl
If set, this URL is added to the start of $wgUploadPath to form a complete upload URL.
bool $wgFetchCommonsDescriptions
Shortcut for the 'fetchDescription' setting of $wgForeignFileRepos.
$wgGroupPermissions
Permission keys given to users in each group.
$wgRestPath
The URL path to the REST API Defaults to "{$wgScriptPath}/rest.php".
string $wgSharedThumbnailScriptPath
Shortcut for the 'thumbScriptUrl' setting of $wgForeignFileRepos.
$wgLocalFileRepo
File repository structures.
$wgDeletedDirectory
What directory to place deleted uploads in.
$wgScriptPath
The path we should point to.
$wgWANObjectCaches
Advanced WAN object cache configuration.
$wgAllowHTMLEmail
For parts of the system that have been updated to provide HTML email content, send both text and HTML...
array false $wgLogos
Specification for different versions of the wiki logo.
$wgExtensionAssetsPath
The URL path of the extensions directory.
$wgForeignFileRepos
Enable the use of files from one or more other wikis.
$wgRepositoryBaseUrl
Shortcut for the 'descBaseUrl' setting of $wgForeignFileRepos.
$wgLogHeaders
Lists the message key string for descriptive text to be shown at the top of each log type.
int null $wgRequestTimeLimit
Set a limit on server request wall clock time.
$wgSharedDB
Shared database for multiple wikis.
$wgDebugDumpSql
Write SQL queries to the debug log.
$wgDatabaseReplicaLagWarning
If lag is higher than $wgDatabaseReplicaLagWarning, show a warning in some special pages (like watchl...
$wgDBserver
Database host name or IP address.
bool $wgForceHTTPS
If this is true, when an insecure HTTP request is received, always redirect to HTTPS.
$wgLoadScript
The URL path to load.php.
$wgCookieSecure
Whether the "secure" flag should be set on the cookie.
$wgMimeTypeExclusions
Files with these MIME types will never be allowed as uploads if $wgVerifyMimeType is enabled.
$wgExtraLanguageCodes
List of mappings from one language code to another.
$wgCanonicalServer
Canonical URL of the server, to use in IRC feeds and notification e-mails.
$wgStylePath
The URL path of the skins directory.
$wgServer
URL of the server.
$wgMinimalPasswordLength
Specifies the minimal length of a user password.
$wgMetaNamespace
Name of the project namespace.
$wgLogo
The URL path of the wiki logo.
$wgSharedSchema
$wgPasswordSender
Sender email address for e-mail notifications.
$wgLogActionsHandlers
The same as above, but here values are names of classes, not messages.
string $wgSharedUploadPath
Shortcut for the 'url' setting of $wgForeignFileRepos.
$wgLocalTZoffset
Set an offset from UTC in minutes to use for the default timezone setting for anonymous users and new...
$wgSharedPrefix
$wgMainWANCache
Main Wide-Area-Network cache type.
$wgDBpassword
Database user's password.
$wgFavicon
The URL path of the shortcut icon.
$wgShowEXIF
Show Exif data, on by default if available.
$wgNewUserLog
Maintain a log of newusers at Special:Log/newusers?
const MW_VERSION
The running version of MediaWiki.
Definition Defines.php:36
const NS_MEDIAWIKI
Definition Defines.php:72
const PROTO_HTTP
Definition Defines.php:191
wfParseUrl( $url)
parse_url() work-alike, but non-broken.
wfTempDir()
Tries to get the system directory for temporary files.
wfWarn( $msg, $callerOffset=1, $level=E_USER_NOTICE)
Send a warning either to the debug log or in a PHP error depending on $wgDevelopmentWarnings.
wfMemoryLimit( $newLimit)
Raise PHP's memory limit (if needed).
wfIniGetBool( $setting)
Safety wrapper around ini_get() for boolean settings.
wfExpandUrl( $url, $defaultProto=PROTO_CURRENT)
Expand a potentially local URL to a fully-qualified URL.
wfDebugLog( $logGroup, $text, $dest='all', array $context=[])
Send a line to a supplementary debug log file, if configured, or main debug log if not.
wfDeprecated( $function, $version=false, $component=false, $callerOffset=2)
Logs a warning that a deprecated feature was used.
global $wgRequest
Definition Setup.php:807
$wgFileExtensions
Definition Setup.php:378
if(is_array($wgExtraNamespaces)) if(count( $wgDummyLanguageCodes) !==0) $wgDummyLanguageCodes
Definition Setup.php:623
$wgEnotifWatchlist
Definition Setup.php:584
$wgEnotifMaxRecips
Definition Setup.php:579
$wgEnotifUserTalk
Definition Setup.php:583
$wgUser
Definition Setup.php:934
$wgEnableUserEmail
Definition Setup.php:576
$rcMaxAgeDays
Definition Setup.php:544
if( $wgShowEXIF===null) $wgGalleryOptions
Determine whether EXIF info can be shown.
Definition Setup.php:445
if(!defined( 'MW_NO_SESSION') &&! $wgCommandLineMode) $wgOut
Definition Setup.php:927
if(!defined( 'MW_NO_SESSION') &&! $wgCommandLineMode) $wgParser
Definition Setup.php:927
if(is_readable("$IP/vendor/autoload.php")) elseif(file_exists("$IP/vendor/autoload.php")) if(!interface_exists(LoggerInterface::class)) global $wgAutoloadClasses
Definition Setup.php:135
global $wgFullyInitialised
Definition Setup.php:963
$wgEnotifFromEditor
Definition Setup.php:577
$wgUseEnotif
Definition Setup.php:586
$wgEnotifRevealEditorAddress
Definition Setup.php:581
if(! $wgCookiePrefix) $wgCookiePrefix
Definition Setup.php:567
$serverParts
Definition Setup.php:756
global $wgInitialSessionId
The persistent session ID (if any) loaded at startup.
Definition Setup.php:807
$wgEnotifImpersonal
Definition Setup.php:578
$wgUsersNotifiedOnAllChanges
Definition Setup.php:588
if( $wgRightsIcon) if(isset($wgFooterIcons[ 'copyright'][ 'copyright']) &&$wgFooterIcons[ 'copyright'][ 'copyright']===[]) if(isset( $wgFooterIcons['poweredby']) &&isset( $wgFooterIcons['poweredby']['mediawiki']) && $wgFooterIcons['poweredby']['mediawiki']['src']===null) $wgNamespaceProtection[NS_MEDIAWIKI]
Unconditional protection for NS_MEDIAWIKI since otherwise it's too easy for a sysadmin to set $wgName...
Definition Setup.php:419
$wgUserEmailUseReplyTo
Definition Setup.php:587
if(! $wgDBerrorLogTZ) $wgCanonicalNamespaceNames
Definitions of the NS_ constants are in Defines.php.
Definition Setup.php:611
if(!defined( 'MW_NO_SESSION') &&! $wgCommandLineMode) $wgLang
Definition Setup.php:927
if(is_readable("$IP/vendor/autoload.php")) elseif(file_exists("$IP/vendor/autoload.php")) if(!interface_exists(LoggerInterface::class)) global $wgConf
$wgConf hold the site configuration.
Definition Setup.php:135
if( $wgServerName !==false) $wgServerName
Definition Setup.php:761
$wgEnotifMinorEdits
Definition Setup.php:580
$wgLockManagers[]
Initialise $wgLockManagers to include basic FS version.
Definition Setup.php:424
$wgDefaultUserOptions['rcdays']
Definition Setup.php:546
if(!defined( 'MW_NO_SESSION') &&! $wgCommandLineMode) $wgTitle
Definition Setup.php:927
$wgEmailAuthentication
Definition Setup.php:575
if($wgServer===false) if( $wgCanonicalServer===false) $wgVirtualRestConfig['global']['domain']
Definition Setup.php:754
global $wgExtensionFunctions
Definition Setup.php:963
if(is_readable("$IP/vendor/autoload.php")) elseif(file_exists("$IP/vendor/autoload.php")) if(!interface_exists(LoggerInterface::class)) global $wgSettings
Pre-config setup: Before loading LocalSettings.php.
Definition Setup.php:121
if(is_readable("$IP/vendor/autoload.php")) elseif(file_exists("$IP/vendor/autoload.php")) if(!interface_exists(LoggerInterface::class)) global $wgCommandLineMode
Definition Setup.php:135
$wgEnotifUseRealName
Definition Setup.php:582
$IP
Definition WebStart.php:51
const MW_ENTRY_POINT
Definition api.php:41
Class to allow throwing wfDeprecated warnings when people use globals that we do not want them to.
Abort the web request with a custom HTML string that will represent the entire response.
static runner()
Get a HookRunner instance for calling hooks using the new interfaces.
Definition Hooks.php:173
Show an error that looks like an HTTP server error.
Definition HttpError.php:32
static setup()
Definition MWDebug.php:80
PSR-3 logger instance factory.
MediaWikiServices is the service locator for the application scope of MediaWiki.
Utility for loading LocalSettings files.
Utility for loading settings files.
Settings loaded from a PHP file path as an array structure.
Utility for loading site-specific settings in a multi-tenancy ("wiki farm" or "wiki family") environm...
static newFromKey( $key,... $params)
Factory function that is just wrapper for the real constructor.
Definition Message.php:399
static schedulePingback()
Schedule a deferred callable that will check if a pingback should be sent and (if so) proceed to send...
Definition Pingback.php:290
static getMain()
Get the RequestContext object associated with the main request.
This is a class for holding configuration settings, particularly for multi-wiki sites.
Stub object for the global user ($wgUser) that makes it possible to change the relevant underlying ob...
static bool $destructorDeprecationDisarmed
Stub object for the user language.
static detectProtocol()
Detect the protocol from $_SERVER.
const MW_CONFIG_CALLBACK
Definition install.php:30
const MW_NO_SESSION
Definition load.php:32
$debug
Definition mcc.php:31
A helper class for throttling authentication attempts.
const DBO_DEFAULT
Definition defines.php:13
const DBO_DEBUG
Definition defines.php:9