From c319cc8968f556e7c5241bc461e296bbb1b12152 Mon Sep 17 00:00:00 2001 From: Chad Horohoe Date: Fri, 9 Oct 2009 12:52:16 +0000 Subject: [PATCH] (bug 13750) $wgCapitalLinks should be a per-namespace setting --- RELEASE-NOTES | 3 +- docs/export-0.4.xsd | 6 ++-- includes/DefaultSettings.php | 22 +++++++++--- includes/Export.php | 6 +++- includes/Namespace.php | 34 ++++++++++++++++++- includes/Setup.php | 2 -- includes/Title.php | 18 ++++++++-- includes/User.php | 7 ++-- includes/api/ApiQuerySiteinfo.php | 3 +- includes/filerepo/FileRepo.php | 4 +-- includes/specials/SpecialCategories.php | 5 +-- includes/specials/SpecialWithoutinterwiki.php | 9 ++--- includes/upload/UploadBase.php | 5 +-- 13 files changed, 88 insertions(+), 36 deletions(-) diff --git a/RELEASE-NOTES b/RELEASE-NOTES index d13dddf9ea..5de904c2fd 100644 --- a/RELEASE-NOTES +++ b/RELEASE-NOTES @@ -89,6 +89,7 @@ it from source control: http://www.mediawiki.org/wiki/Download_from_SVN maintenance * New hook AbortNewAccountAuto, called before account creation from AuthPlugin- or ExtUser-driven requests. +* $wgCapitalLinkOverrides added to configure per-namespace capitalization === New features in 1.16 === @@ -241,7 +242,7 @@ it from source control: http://www.mediawiki.org/wiki/Download_from_SVN called after a user's email has been successfully confirmed or invalidated. * (bug 19741) Moved the XCF files out of the main MediaWiki distribution, for a smaller subversion checkout. - +* (bug 13750) First letter capitalization can now be a per-namespace setting === Bug fixes in 1.16 === diff --git a/docs/export-0.4.xsd b/docs/export-0.4.xsd index f40a3f24bf..3821b630d2 100644 --- a/docs/export-0.4.xsd +++ b/docs/export-0.4.xsd @@ -10,8 +10,9 @@ as a list of defined namespaces. Version 0.4 adds per-revision delete flags, log exports, - discussion threading data, and a per-page redirect flag. - + discussion threading data, a per-page redirect flag, and + per-namespace capitalization. + The canonical URL to the schema document is: http://www.mediawiki.org/xml/export-0.4.xsd @@ -90,6 +91,7 @@ + diff --git a/includes/DefaultSettings.php b/includes/DefaultSettings.php index b990d25f1c..c135b374b9 100644 --- a/includes/DefaultSettings.php +++ b/includes/DefaultSettings.php @@ -213,10 +213,10 @@ $wgImgAuthPublicTest = true; ///< defaults to true - if public read is turned on * thumbScriptUrl The URL for thumb.php (optional, not recommended) * transformVia404 Whether to skip media file transformation on parse and rely on a 404 * handler instead. - * initialCapital Equivalent to $wgCapitalLinks, determines whether filenames implicitly - * start with a capital letter. The current implementation may give incorrect - * description page links when the local $wgCapitalLinks and initialCapital - * are mismatched. + * initialCapital Equivalent to $wgCapitalLinks (or $wgCapitalLinkOverrides[NS_FILE], + * determines whether filenames implicitly start with a capital letter. + * The current implementation may give incorrect description page links + * when the local $wgCapitalLinks and initialCapital are mismatched. * pathDisclosureProtection * May be 'paranoid' to remove all parameters from error messages, 'none' to * leave the paths in unchanged, or 'simple' to replace paths with @@ -2436,6 +2436,18 @@ $wgShowCreditsIfMax = true; */ $wgCapitalLinks = true; +/** + * @since 1.16 - This can now be set per-namespace. Some special namespaces (such + * as Special, see Namespace::$alwaysCapitalizedNamespaces for the full list) must be + * true by default (and setting them has no effect), due to various things that + * require them to be so. Also, since Talk namespaces need to directly mirror their + * associated content namespaces, the values for those are ignored in favor of the + * subject namespace's setting. Setting for NS_MEDIA is taken automatically from + * NS_FILE. + * EX: $wgCapitalLinkOverrides[ NS_FILE ] = false; + */ +$wgCapitalLinkOverrides = array(); + /** * List of interwiki prefixes for wikis we'll accept as sources for * Special:Import (for sysops). Since complete page history can be imported, @@ -3448,7 +3460,7 @@ $wgNamespaceRobotPolicies = array(); * 'Main_Page' => 'noindex,follow', * # "Project", not the actual project name! * 'Project:X' => 'index,follow', - * # Needs to be "Abc", not "abc" (unless $wgCapitalLinks is false)! + * # Needs to be "Abc", not "abc" (unless $wgCapitalLinks is false for that namespace)! * 'abc' => 'noindex,nofollow' * ); */ diff --git a/includes/Export.php b/includes/Export.php index c33ff42cd4..dd58d4b869 100644 --- a/includes/Export.php +++ b/includes/Export.php @@ -414,7 +414,11 @@ class XmlDumpWriter { global $wgContLang; $spaces = "\n"; foreach( $wgContLang->getFormattedNamespaces() as $ns => $title ) { - $spaces .= ' ' . Xml::element( 'namespace', array( 'key' => $ns ), $title ) . "\n"; + $spaces .= ' ' . + Xml::element( 'namespace', + array( 'key' => $ns, + 'case' => MWNamespace::isCapitalized( $ns ) ? 'first-letter' : 'case-sensitive', + ), $title ) . "\n"; } $spaces .= " "; return $spaces; diff --git a/includes/Namespace.php b/includes/Namespace.php index 3d618e649f..f9c23111e6 100644 --- a/includes/Namespace.php +++ b/includes/Namespace.php @@ -45,6 +45,13 @@ if( is_array( $wgExtraNamespaces ) ) { class MWNamespace { + /** + * These namespaces should always be first-letter capitalized, now and + * forevermore. Historically, they could've probably been lowercased too, + * but some things are just too ingrained now. :) + */ + private static $alwaysCapitalizedNamespaces = array( NS_SPECIAL, NS_MEDIAWIKI ); + /** * Can pages in the given namespace be moved? * @@ -181,5 +188,30 @@ class MWNamespace { global $wgNamespacesWithSubpages; return !empty( $wgNamespacesWithSubpages[$index] ); } - + + /** + * Is the namespace first-letter capitalized? + * + * @param $index int Index to check + * @return bool + */ + public static function isCapitalized( $index ) { + global $wgCapitalLinks, $wgCapitalLinkOverrides; + // Turn NS_MEDIA into NS_FILE + $index = $index === NS_MEDIA ? NS_FILE : $index; + + // Make sure to get the subject of our namespace + $index = self::getSubject( $index ); + + // Some namespaces are special and should always be upper case + if ( in_array( $index, self::$alwaysCapitalizedNamespaces ) ) { + return true; + } + if ( isset( $wgCapitalLinkOverrides[ $index ] ) ) { + // $wgCapitalLinkOverrides is explicitly set + return $wgCapitalLinkOverrides[ $index ]; + } + // Default to the global setting + return $wgCapitalLinks; + } } diff --git a/includes/Setup.php b/includes/Setup.php index c73620767a..2f16ed4b90 100644 --- a/includes/Setup.php +++ b/includes/Setup.php @@ -8,7 +8,6 @@ * MEDIAWIKI is defined */ if( !defined( 'MEDIAWIKI' ) ) { - echo "This file is part of MediaWiki, it is not a valid entry point.\n"; exit( 1 ); } @@ -87,7 +86,6 @@ if ( !$wgLocalFileRepo ) { 'hashLevels' => $wgHashedUploadDirectory ? 2 : 0, 'thumbScriptUrl' => $wgThumbnailScriptPath, 'transformVia404' => !$wgGenerateThumbnailOnParse, - 'initialCapital' => $wgCapitalLinks, 'deletedDir' => $wgFileStore['deleted']['directory'], 'deletedHashLevels' => $wgFileStore['deleted']['hash'] ); diff --git a/includes/Title.php b/includes/Title.php index dd6e3897d1..134ad280e4 100644 --- a/includes/Title.php +++ b/includes/Title.php @@ -2229,6 +2229,18 @@ class Title { return $rxTc; } + + /** + * Capitalize a text if it belongs to a namespace that capitalizes + */ + public static function capitalize( $text, $ns = NS_MAIN ) { + global $wgContLang; + + if ( MWNamespace::isCapitalized( $ns ) ) + return $wgContLang->ucfirst( $text ); + else + return $text; + } /** * Secure and split - main initialisation function for this object @@ -2241,7 +2253,7 @@ class Title { * @return \type{\bool} true on success */ private function secureAndSplit() { - global $wgContLang, $wgLocalInterwiki, $wgCapitalLinks; + global $wgContLang, $wgLocalInterwiki; # Initialisation $rxTc = self::getTitleInvalidRegex(); @@ -2403,8 +2415,8 @@ class Title { * site might be case-sensitive. */ $this->mUserCaseDBKey = $dbkey; - if( $wgCapitalLinks && $this->mInterwiki == '') { - $dbkey = $wgContLang->ucfirst( $dbkey ); + if( $this->mInterwiki == '') { + $dbkey = self::capitalize( $dbkey, $this->mNamespace ); } /** diff --git a/includes/User.php b/includes/User.php index 7b9b5aeff9..a5a5423cab 100644 --- a/includes/User.php +++ b/includes/User.php @@ -521,7 +521,7 @@ class User { || User::isIP( $name ) || strpos( $name, '/' ) !== false || strlen( $name ) > $wgMaxNameChars - || $name != $wgContLang->ucfirst( $name ) ) { + || $name != Title::capitalize( $name, NS_USER ) ) { wfDebugLog( 'username', __METHOD__ . ": '$name' invalid due to empty, IP, slash, length, or lowercase" ); return false; @@ -669,9 +669,8 @@ class User { * - 'creatable' Valid for batch processes, login and account creation */ static function getCanonicalName( $name, $validate = 'valid' ) { - # Force usernames to capital - global $wgContLang; - $name = $wgContLang->ucfirst( $name ); + # Maybe force usernames to capital + $name = Title::capitalize( $name, NS_USER ); # Reject names containing '#'; these will be cleaned up # with title normalisation, but then it's too late to diff --git a/includes/api/ApiQuerySiteinfo.php b/includes/api/ApiQuerySiteinfo.php index 8b84b70172..8439e471a2 100644 --- a/includes/api/ApiQuerySiteinfo.php +++ b/includes/api/ApiQuerySiteinfo.php @@ -164,7 +164,8 @@ class ApiQuerySiteinfo extends ApiQueryBase { foreach( $wgContLang->getFormattedNamespaces() as $ns => $title ) { $data[$ns] = array( - 'id' => intval($ns) + 'id' => intval($ns), + 'case' => MWNamespace::isCapitalized( $ns ) ? 'first-letter' : 'case-sensitive', ); ApiResult :: setContent( $data[$ns], $title ); $canonical = MWNamespace::getCanonicalName( $ns ); diff --git a/includes/filerepo/FileRepo.php b/includes/filerepo/FileRepo.php index 64a7bfd49b..24cdfa24b0 100644 --- a/includes/filerepo/FileRepo.php +++ b/includes/filerepo/FileRepo.php @@ -28,7 +28,7 @@ abstract class FileRepo { $this->name = $info['name']; // Optional settings - $this->initialCapital = true; // by default + $this->initialCapital = MWNamespace::isCapitalized( NS_FILE ); foreach ( array( 'descBaseUrl', 'scriptDirUrl', 'articleUrl', 'fetchDescription', 'thumbScriptUrl', 'initialCapital', 'pathDisclosureProtection', 'descriptionCacheExpiry', 'hashLevels', 'url', 'thumbUrl' ) as $var ) @@ -256,7 +256,7 @@ abstract class FileRepo { */ function getNameFromTitle( $title ) { global $wgCapitalLinks; - if ( $this->initialCapital != $wgCapitalLinks ) { + if ( $this->initialCapital != MWNamespace::isCapitalized( NS_FILE ) ) { global $wgContLang; $name = $title->getUserCaseDBKey(); if ( $this->initialCapital ) { diff --git a/includes/specials/SpecialCategories.php b/includes/specials/SpecialCategories.php index d2d03eba43..a649eafd48 100644 --- a/includes/specials/SpecialCategories.php +++ b/includes/specials/SpecialCategories.php @@ -36,10 +36,7 @@ class CategoryPager extends AlphabeticPager { parent::__construct(); $from = str_replace( ' ', '_', $from ); if( $from !== '' ) { - global $wgCapitalLinks, $wgContLang; - if( $wgCapitalLinks ) { - $from = $wgContLang->ucfirst( $from ); - } + $from = Title::capitalize( $from, NS_CATEGORY ); $this->mOffset = $from; } } diff --git a/includes/specials/SpecialWithoutinterwiki.php b/includes/specials/SpecialWithoutinterwiki.php index 2092e43b52..740b43466f 100644 --- a/includes/specials/SpecialWithoutinterwiki.php +++ b/includes/specials/SpecialWithoutinterwiki.php @@ -75,13 +75,10 @@ class WithoutInterwikiPage extends PageQueryPage { } function wfSpecialWithoutinterwiki() { - global $wgRequest, $wgContLang, $wgCapitalLinks; + global $wgRequest, $wgContLang; list( $limit, $offset ) = wfCheckLimits(); - if( $wgCapitalLinks ) { - $prefix = $wgContLang->ucfirst( $wgRequest->getVal( 'prefix' ) ); - } else { - $prefix = $wgRequest->getVal( 'prefix' ); - } + // Only searching the mainspace anyway + $prefix = Title::capitalize( $wgRequest->getVal( 'prefix' ), NS_MAIN ); $wip = new WithoutInterwikiPage(); $wip->setPrefix( $prefix ); $wip->doQuery( $offset, $limit ); diff --git a/includes/upload/UploadBase.php b/includes/upload/UploadBase.php index 700338f8b5..8d8de4eac0 100644 --- a/includes/upload/UploadBase.php +++ b/includes/upload/UploadBase.php @@ -305,10 +305,7 @@ abstract class UploadBase { * but ignore things like ucfirst() and spaces/underscore things */ $comparableName = str_replace( ' ', '_', $this->mDesiredDestName ); - global $wgCapitalLinks, $wgContLang; - if ( $wgCapitalLinks ) { - $comparableName = $wgContLang->ucfirst( $comparableName ); - } + $comparableName = Title::capitalize( $comparableName, NS_FILE ); if( $this->mDesiredDestName != $filename && $comparableName != $filename ) $warnings['badfilename'] = $filename; -- 2.20.1