r92559 MediaWiki - Code Review archive

Repository:MediaWiki
Revision:r92558‎ | r92559 | r92560 >
Date:19:51, 19 July 2011
Author:robin
Status:resolved (Comments)
Tags:
Comment:
Major update of stable features from development code.
* For non-existing info pages (Wx/xx[x] pages), add a welcome page (either missing, existing or closed wikis)
* It automatically checks the database list if available (which is the case on WMF wikis), like SiteMatrix
* Pages belonging to existing wikis are not editable and show a link to the existing wiki. You will be redirected automatically if URL &testwiki or your preference is set to that test wiki.
* Show a logo per-project, and possibility to set it per-wiki (if URL &testwiki or your preference is set to that test wiki)
This is developed against 1.17wmf1 so everything should work on Incubator itself.
Modified paths:
  • /trunk/extensions/WikimediaIncubator/IncubatorTest.php (modified) (history)
  • /trunk/extensions/WikimediaIncubator/InfoPage.css (added) (history)
  • /trunk/extensions/WikimediaIncubator/InfoPage.i18n.php (added) (history)
  • /trunk/extensions/WikimediaIncubator/InfoPage.php (added) (history)
  • /trunk/extensions/WikimediaIncubator/WikimediaIncubator.i18n.php (modified) (history)
  • /trunk/extensions/WikimediaIncubator/WikimediaIncubator.php (modified) (history)

Diff [purge]

Index: trunk/extensions/WikimediaIncubator/InfoPage.css
@@ -0,0 +1,55 @@
 2+.wminc-infopage-title {
 3+ padding:8px;
 4+ font-size:180%;
 5+}
 6+.wminc-infopage-entertest {
 7+ margin-left:1em;
 8+}
 9+.noarticletext, .mw-warning-with-logexcerpt, .firstHeading {
 10+ display: none;
 11+}
 12+.wminc-infopage {
 13+ font-size: 125%;
 14+ font-family: 'Lucida Sans', Verdana, sans-serif;
 15+ padding: .6em; margin: .5em 0;
 16+}
 17+.wminc-infopage p, .wminc-infopage li {
 18+ padding:.2em 0 .3em;
 19+}
 20+.wminc-infopage-welcome {
 21+ font-style: italic;
 22+}
 23+ul.wminc-infopage-otherprojects, ul.wminc-infopage-multilingualprojects {
 24+ list-style: none;
 25+}
 26+.wminc-infopage-otherprojects li, .wminc-infopage-multilingualprojects li {
 27+ display: inline;
 28+ padding:.5em;
 29+}
 30+.wminc-infopage-title {
 31+ font-size:145%;
 32+ padding:.3em 0;
 33+ font-weight:bold;
 34+}
 35+.wminc-infopage-text {
 36+ font-size: 125%;
 37+}
 38+.wminc-infopage-options {
 39+ padding: .2em;
 40+}
 41+.wminc-infopage-logo {
 42+ float: right;
 43+}
 44+.wminc-infopage-createmainpage {
 45+ margin-left: .5em;
 46+ font-weight: bold;
 47+}
 48+.wminc-infopage-status {
 49+ margin: 1em;
 50+}
 51+#ca-nstab-main a {
 52+ color: black;
 53+}
 54+#siteNotice {
 55+ border-bottom: 1px solid silver;
 56+}
\ No newline at end of file
Property changes on: trunk/extensions/WikimediaIncubator/InfoPage.css
___________________________________________________________________
Added: svn:eol-style
157 + native
Index: trunk/extensions/WikimediaIncubator/WikimediaIncubator.php
@@ -14,7 +14,7 @@
1515 'path' => __FILE__,
1616 'name' => 'Wikimedia Incubator',
1717 'author' => 'SPQRobin',
18 - 'version' => '3.2',
 18+ 'version' => '4.0',
1919 'url' => 'http://www.mediawiki.org/wiki/Extension:WikimediaIncubator',
2020 'descriptionmsg' => 'wminc-desc',
2121 );
@@ -22,7 +22,8 @@
2323 /* General (globals and/or configuration) */
2424 $wmincPref = 'incubatortestwiki'; // Name of the preference
2525 $dir = dirname( __FILE__ ) . '/';
26 -// only one-letter codes can be used for projects
 26+$wmincScriptDir = $wgScriptPath . '/extensions/WikimediaIncubator/';
 27+# only one-letter codes can be used for projects
2728 $wmincProjects = array(
2829 'p' => 'Wikipedia',
2930 'b' => 'Wikibooks',
@@ -35,6 +36,12 @@
3637 's' => 'Wikisource',
3738 'v' => 'Wikiversity',
3839 );
 40+$wmincMultilingualProjects = array(
 41+ 'meta.wikimedia.org' => 'Meta-Wiki',
 42+ 'commons.wikimedia.org' => 'Wikimedia Commons',
 43+ 'species.wikimedia.org' => 'Wikispecies',
 44+ 'mediawiki.org' => 'MediaWiki',
 45+);
3946 $wmincProjectSite = array(
4047 'name' => 'Incubator',
4148 'short' => 'inc',
@@ -83,7 +90,7 @@
8491 $wgSpecialPages['MyMainPage'] = 'SpecialMyMainPage';
8592
8693 /* Create/move page permissions */
87 -$wgHooks['getUserPermissionsErrors'][] = 'IncubatorTest::checkPrefixCreatePermissions';
 94+$wgHooks['getUserPermissionsErrors'][] = 'IncubatorTest::onGetUserPermissionsErrors';
8895 $wgHooks['AbortMove'][] = 'IncubatorTest::checkPrefixMovePermissions';
8996
9097 /* Recent Changes */
@@ -99,3 +106,35 @@
100107 /* Random page by test */
101108 $wgAutoloadClasses['SpecialRandomByTest'] = $dir . 'SpecialRandomByTest.php';
102109 $wgSpecialPages['RandomByTest'] = 'SpecialRandomByTest';
 110+
 111+/* support for automatic checking in a list of databases if a wiki exists */
 112+$wmincExistingWikis = $wgLocalDatabases;
 113+/* Stupid "wiki" referring to "wikipedia" in WMF config */
 114+$wmincProjectDatabases = array(
 115+ 'p' => 'wiki',
 116+ 'b' => 'wikibooks',
 117+ 't' => 'wiktionary',
 118+ 'q' => 'wikiquote',
 119+ 'n' => 'wikinews',
 120+ 's' => 'wikisource',
 121+ 'v' => 'wikiversity',
 122+);
 123+# if WMF/SiteMatrix config is available, use it
 124+# NOTICE: include SiteMatrix extension before this extension (this is the case for WMF)
 125+$wmincClosedWikis = isset( $wgSiteMatrixClosedSites ) ? $wgSiteMatrixClosedSites : null;
 126+
 127+/* Wx/xx[x] info page */
 128+$wgAutoloadClasses['InfoPage'] = $dir . 'InfoPage.php';
 129+$wgExtensionMessagesFiles['InfoPage'] = $dir . 'InfoPage.i18n.php';
 130+$wgHooks['ShowMissingArticle'][] = 'IncubatorTest::onShowMissingArticle';
 131+$wgHooks['EditFormPreloadText'][] = 'IncubatorTest::onEditFormPreloadText';
 132+$wgHooks['ArticleFromTitle'][] = 'IncubatorTest::onArticleFromTitle';
 133+
 134+$wgResourceModules['WikimediaIncubator.InfoPage'] = array(
 135+ 'styles' => 'InfoPage.css',
 136+ 'localBasePath' => dirname(__FILE__),
 137+ 'remoteExtPath' => $wmincScriptDir,
 138+);
 139+
 140+/* Possibility to set a logo per test wiki */
 141+$wgHooks['BeforePageDisplay'][] = 'IncubatorTest::fnTestWikiLogo';
Index: trunk/extensions/WikimediaIncubator/IncubatorTest.php
@@ -76,7 +76,9 @@
7777 static function validateLanguageCode( $code ) {
7878 global $wmincLangCodeLength;
7979 if( strlen( $code ) > $wmincLangCodeLength ) { return false; }
80 - if( $code == 'be-x-old' ) { return true; } // one exception...
 80+ if( $code == 'be-x-old' ) {
 81+ return true; # one exception... waiting to be renamed to be-tarask
 82+ }
8183 return (bool) preg_match( '/^[a-z][a-z][a-z]?(-[a-z]+)?$/', $code );
8284 }
8385
@@ -94,17 +96,17 @@
9597 * @return Array with 'error' or 'project', 'lang', 'prefix' and
9698 * optionally 'realtitle'
9799 */
98 - static function analyzePrefix( $title, $onlyprefix = false ) {
99 - $data = array();
100 - // split title into parts
 100+ static function analyzePrefix( $title, $onlyInfoPage = false ) {
 101+ $data = array( 'error' => null );
 102+ # split title into parts
101103 $titleparts = explode( '/', $title );
102104 if( !is_array( $titleparts ) || !isset( $titleparts[1] ) ) {
103105 $data['error'] = 'noslash';
104106 } else {
105 - $data['project'] = ( isset( $titleparts[0][1] ) ? $titleparts[0][1] : '' ); // get the x from Wx/...
106 - $data['lang'] = $titleparts[1];
 107+ $data['project'] = ( isset( $titleparts[0][1] ) ? $titleparts[0][1] : '' ); # get the x from Wx/...
 108+ $data['lang'] = $titleparts[1]; # language code
107109 $data['prefix'] = 'W'.$data['project'].'/'.$data['lang'];
108 - // check language code
 110+ # check language code
109111 if( !self::validateLanguageCode( $data['lang'] ) ) {
110112 $data['error'] = 'invalidlangcode';
111113 }
@@ -112,16 +114,15 @@
113115 global $wmincProjects;
114116 $listProjects = implode( '', array_keys( $wmincProjects ) ); # something like: pbtqn
115117 if( !preg_match( '/^W['.$listProjects.']\/[a-z-]+' .
116 - ($onlyprefix ? '$/' : '(\/.+)?$/' ), $title ) ) {
 118+ ($onlyInfoPage ? '$/' : '(\/.+)?$/' ), $title ) ) {
117119 $data['error'] = 'invalidprefix';
118120 }
119 - if( !$onlyprefix && ( isset( $data['error'] ) &&
120 - $data['error'] != 'invalidprefix' ) ) { // there is a Page_title
121 - $prefixn = strlen( $data['prefix'].'/' ); // number of chars in prefix
122 - // get Page_title from Wx/xx/Page_title
 121+ if( !$onlyInfoPage && $data['error'] != 'invalidprefix' ) { # there is a Page_title
 122+ $prefixn = strlen( $data['prefix'].'/' ); # number of chars in prefix
 123+ # get Page_title from Wx/xx/Page_title
123124 $data['realtitle'] = substr( $title, $prefixn );
124125 }
125 - return $data; // return an array with information
 126+ return $data; # return an array with information
126127 }
127128
128129 /**
@@ -130,7 +131,7 @@
131132 */
132133 static function validatePrefix( $title, $onlyprefix = false ) {
133134 $data = self::analyzePrefix( $title, $onlyprefix );
134 - if( !isset( $data['error'] ) ) { return true; }
 135+ if( !$data['error'] ) { return true; }
135136 return false;
136137 }
137138
@@ -246,41 +247,68 @@
247248 }
248249
249250 /**
250 - * Return an error if the user wants to create an unprefixed page
 251+ * Whether we should show an error message that the page is unprefixed
 252+ * @param $title Title object
251253 * @return Boolean
252254 */
253 - static function checkPrefixCreatePermissions( $title, $user, $action, &$result ) {
254 - global $wmincProjectSite, $wmincTestWikiNamespaces, $wmincPseudoCategoryNSes;
255 - $titletext = $title->getText();
 255+ static function shouldWeShowUnprefixedError( $title ) {
 256+ global $wmincTestWikiNamespaces, $wmincProjectSite;
 257+ $prefixdata = self::analyzePrefix( $title->getText() );
256258 $ns = $title->getNamespace();
257 - $prefixdata = self::analyzePrefix( $titletext );
258 - if( $action != 'create' ) {
259 - // only check on page creation
260 - return true;
 259+ if( !$prefixdata['error'] ) {
 260+ # no error in prefix -> no error to show
 261+ return false;
261262 } elseif( self::displayPrefix() == $wmincProjectSite['short'] ) {
262 - // If user has "project" as test wiki preference, it isn't needed to check
263 - return true;
 263+ # If user has "project" (Incubator) as test wiki preference, it isn't needed to check
 264+ return false;
264265 } elseif( !in_array( $ns, $wmincTestWikiNamespaces ) ) {
265 - // OK if it's not in one of the content namespaces
 266+ # OK if it's not in one of the content namespaces
 267+ return false;
 268+ } elseif( ( $ns == NS_CATEGORY || $ns == NS_CATEGORY_TALK ) &&
 269+ preg_match( '/^(' . implode( '|', $wmincPseudoCategoryNSes ) .'):.+$/', $title->getText() ) ) {
 270+ # whitelisted unprefixed categories
 271+ return false;
 272+ }
 273+ return true;
 274+ }
 275+
 276+ /**
 277+ * This does several things:
 278+ * Disables editing pages belonging to existing wikis (+ shows message)
 279+ * Disables creating an unprefixed page (+ shows error message)
 280+ * See also: IncubatorTest::onShowMissingArticle()
 281+ * @return Boolean
 282+ */
 283+ static function onGetUserPermissionsErrors( $title, $user, $action, &$result ) {
 284+ $titletext = $title->getText();
 285+ $prefixdata = self::analyzePrefix( $titletext );
 286+
 287+ if( self::getDBState( $prefixdata ) == 'existing' ) {
 288+ if( $prefixdata['prefix'] == $titletext &&
 289+ ( $title->exists() || $user->isAllowed( 'editinterface' ) ) ) {
 290+ # if it's an info page, allow if the page exists or the user has 'editinterface' right
 291+ return true;
 292+ }
 293+ # no permission if the wiki already exists
 294+ $link = self::getSubdomain( $prefixdata['lang'],
 295+ $prefixdata['project'], ( $title->getNsText() ? $title->getNsText() . ':' : '' ) .
 296+ preg_replace( '/ /', '_', $prefixdata['realtitle'] ) );
 297+ $result[] = array( 'wminc-error-wiki-exists', $link );
 298+ return false;
 299+ }
 300+
 301+ if( !self::shouldWeShowUnprefixedError( $title ) || $action != 'create' ) {
 302+ # only check if needed & if on page creation
266303 return true;
267 - } elseif( !isset( $prefixdata['error'] ) ) {
268 - // no error in prefix -> no error to show
269 - return true;
270 - } elseif( ($ns == NS_CATEGORY || $ns == NS_CATEGORY_TALK) &&
271 - preg_match('/^('.implode('|',$wmincPseudoCategoryNSes).'):.+$/', $titletext) ) {
272 - // whitelisting
273 - return true;
274304 } elseif( $prefixdata['error'] == 'invalidlangcode' ) {
275305 $error[] = array( 'wminc-error-wronglangcode', $prefixdata['lang'] );
276306 } elseif ( self::isContentProject() ) {
277 - // If the user has a test wiki pref, suggest a page title with prefix
278 - $suggesttitle = (isset( $prefixdata['realtitle'] ) ?
279 - $prefixdata['realtitle'] : $titletext );
280 - $suggest = self::displayPrefixedTitle( $suggesttitle, $ns );
281 - if ( !$title->exists() ) {
282 - // Creating a page, so suggest to create a prefixed page
283 - $error[] = array( 'wminc-error-unprefixed-suggest', $suggest );
284 - }
 307+ # If the user has a test wiki pref, suggest a page title with prefix
 308+ $suggesttitle = isset( $prefixdata['realtitle'] ) ?
 309+ $prefixdata['realtitle'] : $titletext;
 310+ $suggest = self::displayPrefixedTitle( $suggesttitle, $title->getNamespace() );
 311+ # Suggest to create a prefixed page
 312+ $error[] = array( 'wminc-error-unprefixed-suggest', $suggest );
285313 } else {
286314 $error = 'wminc-error-unprefixed';
287315 }
@@ -294,22 +322,12 @@
295323 * @return Boolean
296324 */
297325 static function checkPrefixMovePermissions( $oldtitle, $newtitle, $user, &$error ) {
298 - global $wmincProjectSite, $wmincTestWikiNamespaces;
299 - $prefixdata = self::analyzePrefix( $newtitle->getText() );
300 - $ns = $newtitle->getNamespace();
301 - if( !isset( $prefixdata['error'] ) ) {
302 - // if there is no error with the page title
303 - return true;
304 - } elseif( self::displayPrefix() == $wmincProjectSite['short'] ) {
305 - // If user has "project" as test wiki preference, it isn't needed to check
306 - return true;
307 - } elseif( !in_array( $ns, $wmincTestWikiNamespaces ) ) {
308 - // OK if it's not in one of the content namespaces
309 - return true;
 326+ if( self::shouldWeShowUnprefixedError( $newtitle ) ) {
 327+ # there should be an error with the new page title
 328+ $error = wfMsgWikiHtml( 'wminc-error-move-unprefixed' );
 329+ return false;
310330 }
311 - // now there should be an error with the new page title
312 - $error = wfMsgWikiHtml( 'wminc-error-move-unprefixed' );
313 - return false;
 331+ return true;
314332 }
315333
316334 /**
@@ -329,4 +347,285 @@
330348 }
331349 return true;
332350 }
333 -}
\ No newline at end of file
 351+
 352+ /**
 353+ * This loads language names. Also from CLDR if that extension is found.
 354+ * @return Array with language names or empty array
 355+ */
 356+ static public function getLanguageNames( $code = '' ) {
 357+ if ( is_callable( array( 'LanguageNames', 'getNames' ) ) ) {
 358+ global $wgLang;
 359+ $langcode = ( $code ? $code : $wgLang->getCode() );
 360+ return LanguageNames::getNames( $langcode,
 361+ LanguageNames::FALLBACK_NORMAL,
 362+ LanguageNames::LIST_MW_AND_CLDR
 363+ );
 364+ }
 365+ return Language::getLanguageNames( false );
 366+ }
 367+
 368+ /**
 369+ * Do we know the databases of the existing wikis?
 370+ * @return Boolean
 371+ */
 372+ static function canWeCheckDB() {
 373+ global $wmincExistingWikis, $wmincProjectDatabases;
 374+ if( !is_array( $wmincProjectDatabases ) ) {
 375+ return false; # We don't know the database names of the projects
 376+ } elseif( !isset( $wmincExistingWikis ) || !is_array( $wmincExistingWikis ) ) {
 377+ return false; # No list of databases
 378+ }
 379+ return true; # Should work now
 380+ }
 381+
 382+ /**
 383+ * Given an incubator testwiki prefix, get the database name of the
 384+ * corresponding wiki, whether it exists or not
 385+ * @param $prefix Array from IncubatorTest::analyzePrefix();
 386+ * @return false or string
 387+ */
 388+ static function getDB( $prefix ) {
 389+ if( !self::canWeCheckDB() ) {
 390+ return false;
 391+ } elseif( !isset( $prefix ) || $prefix['error'] ) {
 392+ return false; # shouldn't be, but you never know
 393+ }
 394+ global $wmincProjectDatabases;
 395+ return preg_replace('/-/', '_', $prefix['lang'] ) .
 396+ $wmincProjectDatabases[$prefix['project']];
 397+ }
 398+
 399+ /**
 400+ * @return false or array with closed databases
 401+ */
 402+ static function getDBClosedWikis() {
 403+ global $wmincClosedWikis;
 404+ if( !self::canWeCheckDB() ) {
 405+ return false;
 406+ }
 407+ # Is probably a file, but it might be that an array is given
 408+ return is_array( $wmincClosedWikis ) ? $wmincClosedWikis :
 409+ array_map( 'trim', file( $wmincClosedWikis ) );
 410+ }
 411+
 412+ /**
 413+ * @param $prefix Array from IncubatorTest::analyzePrefix();
 414+ * @return false or string 'existing' 'closed' 'missing'
 415+ */
 416+ static function getDBState( $prefix ) {
 417+ $db = self::getDB( $prefix );
 418+ if( !$db ) {
 419+ return false;
 420+ }
 421+ global $wmincExistingWikis, $wmincClosedWikis;
 422+ if( !in_array( $db, $wmincExistingWikis ) ) {
 423+ return 'missing'; # not in the list
 424+ } elseif( in_array( $db, self::getDBClosedWikis() ) ) {
 425+ return 'closed'; # in the list of closed wikis
 426+ }
 427+ return 'existing';
 428+ }
 429+
 430+ /**
 431+ * If existing wiki: show message or redirect if &testwiki is set to that
 432+ * Missing article on Wx/xx info pages: show welcome page
 433+ * See also: IncubatorTest::onGetUserPermissionsErrors()
 434+ * @return True
 435+ */
 436+ static function onShowMissingArticle( $article ) {
 437+ global $wgOut, $wgUser;
 438+ $title = $article->getTitle();
 439+ $prefix = self::analyzePrefix( $title->getText(), true /* only info pages */ );
 440+
 441+ if( $prefix['error'] ) { # We are not on info pages
 442+ $prefix2 = self::analyzePrefix( $title->getText() );
 443+ if( self::getDBState( $prefix2 ) == 'existing' ) {
 444+ $link = self::getSubdomain( $prefix2['lang'],
 445+ $prefix2['project'], ( $title->getNsText() ? $title->getNsText() . ':' : '' ) .
 446+ $prefix2['realtitle'] );
 447+ if( self::displayPrefix() == $prefix2['prefix'] ) {
 448+ # Redirect to the existing wiki if the user has this wiki as preference
 449+ $wgOut->redirect( $link );
 450+ return true;
 451+ } else {
 452+ # Show a link to the existing wiki
 453+ $showLink = $wgUser->getSkin()->makeExternalLink( $link, $link );
 454+ $wgOut->addHtml( '<div class="wminc-wiki-exists">' .
 455+ wfMsgHtml( 'wminc-error-wiki-exists', $showLink ) .
 456+ '</div>' );
 457+ }
 458+ } elseif ( self::shouldWeShowUnprefixedError( $title ) ) {
 459+ # Unprefixed pages
 460+ if( self::isContentProject() ) {
 461+ # If the user has a test wiki pref, suggest a page title with prefix
 462+ $suggesttitle = isset( $prefix2['realtitle'] ) ?
 463+ $prefix2['realtitle'] : $title->getText();
 464+ $suggest = self::displayPrefixedTitle( $suggesttitle, $title->getNamespace() );
 465+ # Suggest to create a prefixed page
 466+ $wgOut->addHtml( '<div class="wminc-unprefixed-suggest">' .
 467+ wfMsgWikiHtml( 'wminc-error-unprefixed-suggest', $suggest ) .
 468+ '</div>' );
 469+ } else {
 470+ $wgOut->addWikiMsg( 'wminc-error-unprefixed' );
 471+ }
 472+ }
 473+ return true;
 474+ }
 475+
 476+ # At this point we should be on info pages ("Wx/xx[x]" pages)
 477+ # So use the InfoPage class to show a nice welcome page
 478+ # depending on whether it belongs to an existing, closed or missing wiki
 479+ if( $title->getNamespace() != NS_MAIN ) {
 480+ return true; # not for other namespaces
 481+ }
 482+ $infopage = new InfoPage( $title, $prefix );
 483+ $infopage->mDbStatus = $dbstate = self::getDBState( $prefix );
 484+ if( $dbstate == 'existing' ) {
 485+ $infopage->mSubStatus = 'beforeincubator';
 486+ $wgOut->addHtml( $infopage->showExistingWiki() );
 487+ } elseif( $dbstate == 'closed' ) {
 488+ $infopage->mSubStatus = 'imported';
 489+ $wgOut->addHtml( $infopage->showIncubatingWiki() );
 490+ } else {
 491+ $wgOut->addHtml( $infopage->showMissingWiki() );
 492+ }
 493+ return true;
 494+ }
 495+
 496+ /**
 497+ * When creating a new info page, help the user by prefilling it
 498+ * @return True
 499+ */
 500+ public static function onEditFormPreloadText( &$text, &$title ) {
 501+ $pagetitle = $title->getText();
 502+ $prefix = IncubatorTest::analyzePrefix( $pagetitle, true /* only info page */ );
 503+ if( $prefix['error'] || $title->getNamespace() != NS_MAIN ) {
 504+ return true;
 505+ }
 506+ global $wgRequest, $wgOut;
 507+ if ( $wgRequest->getBool( 'redlink' ) ) {
 508+ # The edit page was reached via a red link.
 509+ # Redirect to the article page and let them click the edit tab if
 510+ # they really want to create this info page.
 511+ $wgOut->redirect( $title->getFullUrl() );
 512+ }
 513+ $text = wfMsgNoTrans( 'wminc-infopage-prefill', $prefix['prefix'] );
 514+ return true;
 515+ }
 516+
 517+ /**
 518+ * TODO: add support for secure server?
 519+ * @return String
 520+ */
 521+ public static function getSubdomain( $lang, $project, $title = '', $protocol = true ) {
 522+ global $wmincProjects;
 523+ $projectName = isset( $wmincProjects[$project] ) ? $wmincProjects[$project] : $project;
 524+ return ( $protocol ? 'http://' : '' ) . strtolower( $lang ) . '.' .
 525+ strtolower( $projectName ) . '.org' . ( $title ? '/wiki/' . $title : '' );
 526+ }
 527+
 528+ /**
 529+ * make "Wx/xxx/Main Page"
 530+ * @return String
 531+ */
 532+ public static function getMainPage( $langCode, $prefix = null ) {
 533+ # Take the "mainpage" msg in the given language
 534+ $msg = wfMsgExt( 'mainpage', array( 'language' => $langCode ) );
 535+ return isset( $prefix ) ? $prefix . '/' . $msg : $msg;
 536+ }
 537+
 538+ /**
 539+ * Redirect if &goto=mainpage on info pages
 540+ * @return True
 541+ */
 542+ public static function onArticleFromTitle( &$title, &$article ) {
 543+ global $wgRequest;
 544+ $prefix = IncubatorTest::analyzePrefix( $title, true );
 545+ if( $prefix['error'] || $wgRequest->getVal('goto') != 'mainpage' ) {
 546+ return true;
 547+ }
 548+ $dbstate = self::getDBState( $prefix );
 549+ if( !$dbstate ) {
 550+ return true;
 551+ }
 552+ if( $dbstate == 'existing' ) {
 553+ $url = self::getSubdomain( $prefix['lang'], $prefix['project'] );
 554+ } else {
 555+ $params = 'redirectfrom=infopage';
 556+ $uselang = $wgRequest->getVal( 'uselang' );
 557+ if( $uselang ) {
 558+ $params .= '&uselang=' . $uselang;
 559+ }
 560+ $mainpage = Title::newFromText(
 561+ self::getMainPage( $prefix['lang'], $prefix['prefix'] )
 562+ );
 563+ $url = $mainpage->getFullURL( $params );
 564+ }
 565+ global $wgOut;
 566+ $wgOut->redirect( $url );
 567+ return true;
 568+ }
 569+
 570+ /**
 571+ * Whether we should use the feature of custom logos per project
 572+ * @param $title Title object
 573+ * @return false or Array from analyzePrefix()
 574+ */
 575+ static function shouldWeSetCustomLogo( $title ) {
 576+ $prefix = IncubatorTest::analyzePrefix( $title->getText() );
 577+
 578+ # Maybe do later something like if( isContentProject() && 'recentchanges' ) { return true; }
 579+
 580+ # return if the page does not have a valid prefix (info page is considered valid)
 581+ if( $prefix['error'] ) {
 582+ return false;
 583+ }
 584+ # display the custom logo only if &testwiki=wx/xx or the user's pref is set to the current test wiki
 585+ if( self::displayPrefix() != $prefix['prefix'] ) {
 586+ return false;
 587+ }
 588+ global $wmincTestWikiNamespaces;
 589+ # return if the page is not in one of the test wiki namespaces
 590+ if( !in_array( $title->getNamespace(), (array)$wmincTestWikiNamespaces ) ) {
 591+ return false;
 592+ }
 593+ return $prefix;
 594+ }
 595+
 596+ /**
 597+ * Display a different logo in current test wiki
 598+ * if it is set in MediaWiki:Incubator-logo-wx/xxx
 599+ * and if accessed through &testwiki=wx/xxx
 600+ * or it the user preference is set to wx/xxx
 601+ * @return Boolean
 602+ */
 603+ static function fnTestWikiLogo( &$out ) {
 604+ $setLogo = self::shouldWeSetCustomLogo( $out->getTitle() );
 605+ if( !$setLogo ) {
 606+ return false;
 607+ }
 608+ global $wgLogo;
 609+ # return if MediaWiki: Incubator-logo-wx/xx(x) does not exists
 610+ $prefixForPageTitle = preg_replace('/\//', '-', strtolower( $setLogo['prefix'] ) );
 611+ $file = wfFindFile( wfMsgForContentNoTrans( 'Incubator-logo-' . $prefixForPageTitle ) );
 612+ if( !$file ) {
 613+ # Try a general, default logo for that project
 614+ global $wmincProjects;
 615+ $project = $setLogo['project'];
 616+ $projectForFile = preg_replace('/ /', '-', strtolower( $wmincProjects[$project] ) );
 617+ $imageobj = wfFindFile( wfMsg( 'wminc-logo-' . $projectForFile ) );
 618+ if( $imageobj ) {
 619+ $thumb = $imageobj->transform( array( 'width' => 135, 'height' => 135 ) );
 620+ $wgLogo = $thumb->getUrl();
 621+ return true;
 622+ }
 623+ return false;
 624+ }
 625+ if ( $file == null ) {
 626+ return false;
 627+ }
 628+ $thumb = $file->transform( array( 'width' => 135, 'height' => 135 ) );
 629+ $wgLogo = $thumb->getUrl();
 630+ return true;
 631+ }
 632+}
Index: trunk/extensions/WikimediaIncubator/InfoPage.i18n.php
@@ -0,0 +1,160 @@
 2+<?php
 3+/**
 4+ * Internationalisation file for WikimediaIncubator extension.
 5+ * @file
 6+ * @ingroup Extensions
 7+ */
 8+
 9+$messages = array();
 10+
 11+/** English
 12+ * @author SPQRobin
 13+ */
 14+$messages['en'] = array(
 15+ 'wminc-infopage-enter' => 'go to the Main Page',
 16+ 'wminc-unknownlang' => '(unknown language with code "$1")',
 17+ 'wminc-logo-wikipedia' => 'Wikipedia-logo-v2-en.svg', # only translate if necessary
 18+ 'wminc-logo-wiktionary' => 'Wiktionary-logo-en.svg', # only translate if necessary
 19+ 'wminc-logo-wikibooks' => 'Wikibooks-logo-en-noslogan.svg', # only translate if necessary
 20+ 'wminc-logo-wikinews' => 'Wikinews-logo-en.png', # only translate if necessary
 21+ 'wminc-logo-wikiquote' => 'Wikiquote-logo-en.svg', # only translate if necessary
 22+ 'wminc-logo-wikisource' => 'Wikisource-newberg-de.png', # only translate if necessary
 23+ 'wminc-logo-wikiversity' => 'Wikiversity-logo-en.svg', # only translate if necessary
 24+ 'wminc-logo-meta-wiki' => 'Metawiki.svg', # only translate if necessary
 25+ 'wminc-logo-wikimedia-commons' => 'Commons-logo-en.svg', # only translate if necessary
 26+ 'wminc-logo-wikispecies' => 'WikiSpecies.svg', # only translate if necessary
 27+ 'wminc-logo-mediawiki' => 'MediaWiki.svg', # only translate if necessary
 28+ 'wminc-manual-url' => 'Help:Manual', # only translate if necessary
 29+ 'wminc-infopage-title' => '$1 $2', # only translate if necessary
 30+ 'wminc-infopage-welcome' => 'Welcome to the Wikimedia Incubator, a project of the Wikimedia Foundation ([[{{MediaWiki:Aboutpage}}|About]])',
 31+
 32+ 'wminc-infopage-missingwiki-text' => 'A $1 in this language does not yet exist.',
 33+ 'wminc-infopage-option-startwiki' => 'If you want to start this wiki,
 34+you can [{{fullurl:{{FULLPAGENAME}}|action=edit}} create the page] and follow [[{{MediaWiki:Wminc-manual-url}}|our manual]].',
 35+ 'wminc-infopage-option-languages-existing' => 'You can search for [http://www.$1.org existing language editions of $1].',
 36+ 'wminc-infopage-option-sisterprojects-existing' => 'You can search for existing projects in this language:',
 37+ 'wminc-infopage-option-sisterprojects-other' => 'You can search for other projects in this language:',
 38+ 'wminc-infopage-option-multilingual' => 'You can go to a multilingual wiki:',
 39+ 'wminc-infopage-createmainpage' => 'Enter the word "Main Page" in this language:',
 40+ 'wminc-infopage-prefill' => '{{test wiki
 41+| status = tocreate
 42+| language = Language name in English
 43+| meta = <!-- is there a request on Meta-Wiki? -->
 44+}}', # do not translate
 45+ 'wminc-infopage-contribute' => 'If you know this language, you are encouraged to contribute!',
 46+
 47+ 'wminc-infopage-status-imported' => 'This Incubator wiki has been imported from $1 after the wiki was closed.',
 48+ 'wminc-infopage-status-created' => 'This project has been approved by the language committee and is now available at $1.',
 49+ 'wminc-infopage-status-beforeincubator' => 'This project was created before Wikimedia Incubator started and is available at $1.',
 50+);
 51+
 52+/** German (Deutsch)
 53+ * @author Polletfa
 54+ * @author Raymond
 55+ */
 56+$messages['de'] = array(
 57+ 'wminc-infopage-contribute' => 'Wenn du diese Sprache beherrschst, bist du herzlich willkommen, mitzumachen!',
 58+);
 59+
 60+/** German (formal address) (‪Deutsch (Sie-Form)‬)
 61+ * @author Polletfa
 62+ * @author Raymond
 63+ */
 64+$messages['de-formal'] = array(
 65+ 'wminc-infopage-contribute' => 'Wenn Sie diese Sprache beherrschen, sind Sie herzlich willkommen, mitzumachen!',
 66+);
 67+
 68+/** Spanish (Español)
 69+ * @author Diotime
 70+ */
 71+$messages['es'] = array(
 72+ 'wminc-infopage-contribute' => '¡Si entiendes esta lengua, te animamos a contribuir!',
 73+);
 74+
 75+/** French (Français)
 76+ * @author
 77+ */
 78+$messages['fr'] = array(
 79+ 'wminc-infopage-contribute' => 'Si vous parlez cette langue, vous êtes invités à contribuer !',
 80+);
 81+
 82+/** Korean (한국어)
 83+ * @author Albamhandae
 84+ */
 85+$messages['ko'] = array(
 86+ 'wminc-infopage-contribute' => '이 시험판에 쓰여진 언어를 아신다면, 기여를 부탁드립니다!',
 87+);
 88+
 89+/** Colognian (Ripoarisch)
 90+ * @author Purodha
 91+ */
 92+$messages['ksh'] = array(
 93+ 'wminc-infopage-contribute' => 'Wann De di Shprooch kanns, dann bes De opjeroofe, beizedraare!',
 94+);
 95+
 96+/** Lithuanian (Lietuvių)
 97+ * @author Matasg
 98+ */
 99+$messages['lt'] = array(
 100+ 'wminc-infopage-contribute' => 'Jei suprantate, ar kalbate šią kalba, esate kviečiama(s) prisidėti!',
 101+);
 102+
 103+/** Dutch (Nederlands)
 104+ * @author SPQRobin
 105+ */
 106+$messages['nl'] = array(
 107+ 'testwiki-enter' => 'Ga naar de hoofdpagina',
 108+ 'wminc-unknownlang' => '(onbekende taal met code "$1")',
 109+ 'wminc-infopage-tocreate-welcome' => 'Welkom op Wikimedia Incubator, een project van de Wikimedia Foundation ([[{{MediaWiki:Aboutpage}}|Meer info]])',
 110+ 'wminc-infopage-tocreate-text' => 'Een $1 in deze taal bestaat nog niet.',
 111+ 'wminc-infopage-contribute' => 'Als u deze taal kent, wordt u aangemoedigd om bij te dragen!',
 112+);
 113+
 114+/** Portuguese (Português)
 115+ * @author Carla404
 116+ */
 117+$messages['pt'] = array(
 118+ 'wminc-infopage-contribute' => 'Se você fala este idioma, está convidado a contribuir!',
 119+);
 120+
 121+/** Russian (Русский)
 122+ * @author Amdf
 123+ */
 124+$messages['ru'] = array(
 125+ 'wminc-infopage-contribute' => 'Если вы понимаете этот язык, вы можете внести свой вклад!',
 126+);
 127+
 128+/** Rusyn (Русиньскый)
 129+ * @author Gazeb
 130+ */
 131+$messages['rue'] = array(
 132+ 'wminc-infopage-contribute' => 'Кідь розумієте тот язык, рекомендуєме, жебы сьте приспівали!',
 133+);
 134+
 135+/** Albanian (Shqip)
 136+ * @author Olsi
 137+ */
 138+$messages['sq'] = array(
 139+ 'wminc-infopage-contribute' => 'Nëse e dini këtë gjuhë, jeni të inkurajuar të kontribuoni!',
 140+);
 141+
 142+/** Ukrainian (Українська)
 143+ * @author Andrijko Z.
 144+ */
 145+$messages['uk'] = array(
 146+ 'wminc-infopage-contribute' => 'Якщо ви розумієте цю мову, ви можете внести свій вклад!',
 147+);
 148+
 149+/** Vietnamese (Tiếng Việt)
 150+ * @author Kimkha
 151+ */
 152+$messages['vi'] = array(
 153+ 'wminc-infopage-contribute' => 'Nếu bạn biết ngôn ngữ này, rất hoan nghênh bạn đóng góp cho nó!',
 154+);
 155+
 156+/** Simplified Chinese (‪中文(简体)‬)
 157+ * @author Dalt
 158+ */
 159+$messages['zh-hans'] = array(
 160+ 'wminc-infopage-contribute' => '如果您会这门语言,欢迎您做出贡献!',
 161+);
Property changes on: trunk/extensions/WikimediaIncubator/InfoPage.i18n.php
___________________________________________________________________
Added: svn:eol-style
1162 + native
Index: trunk/extensions/WikimediaIncubator/InfoPage.php
@@ -0,0 +1,183 @@
 2+<?php
 3+/**
 4+ * Implements the "info page" (Wx/xx pages)
 5+
 6+'missing' showMissingWiki()
 7+ A [Project] in this language does not yet exist.
 8+'incubator' showIncubatingWiki()
 9+ 'open': This is a new Incubator wiki that is not yet verified by the language committee.
 10+ 'eligible': This Incubator wiki has been marked as eligible by the language committee.
 11+ 'imported': This Incubator wiki has been imported from xyz.wikiproject.org after that wiki was closed.
 12+ 'approved': This Incubator wiki has been approved by the language committee and will soon be created.
 13+'existing' showExistingWiki()
 14+ 'created': This project has been approved by the language committee and is now available at xyz.wikiproject.org.
 15+ 'beforeincubator': This project was created before Wikimedia Incubator started and is available at xyz.wikiproject.org.
 16+
 17+ * @file
 18+ * @ingroup Extensions
 19+ * @author Robin Pepermans (SPQRobin)
 20+ */
 21+
 22+class InfoPage {
 23+ public function __construct( $title, $prefixdata ) {
 24+ global $wmincProjects;
 25+ $this->mTitle = $title;
 26+ $this->mPrefix = $prefixdata['prefix'];
 27+ $this->mLangCode = $prefixdata['lang'];
 28+ $this->mProjectCode = $prefixdata['project'];
 29+ $this->mProjectName = isset( $wmincProjects[$this->mProjectCode] ) ?
 30+ $wmincProjects[$this->mProjectCode] : '';
 31+ if( isset( $prefixdata['error'] ) || $title->getNamespace() != NS_MAIN ) {
 32+ return;
 33+ }
 34+ $this->mDBStatus = '';
 35+ $this->mSubStatus = '';
 36+ $this->mThisLangData = array( 'type' => 'valid' ); # For later code check feature
 37+ $this->mLangNames = IncubatorTest::getLanguageNames();
 38+ $this->mLangName = ( isset( $this->mLangNames[$this->mLangCode] ) ?
 39+ $this->mLangNames[$this->mLangCode] : wfMsg( 'wminc-unknownlang', $this->mLangCode ) );
 40+ return;
 41+ }
 42+
 43+ /**
 44+ * Small convenience function to display a (clickable) logo
 45+ * @param $project Project name
 46+ */
 47+ public function makeLogo( $project, $clickable = true, $width = 25, $height = '', $url = '', $args = array() ) {
 48+ global $wgUser;
 49+ $projectForFile = preg_replace('/ /', '-', strtolower( $project ) );
 50+ $imageobj = wfFindFile( wfMsg( 'wminc-logo-' . $projectForFile ) );
 51+ $useUrl = $url ? $url : 'http://www.'.strtolower( $project ).'.org/';
 52+ if ( !$imageobj ) { # image not found
 53+ if( !$clickable ) {
 54+ return $logo;
 55+ }
 56+ return $wgUser->getSkin()->makeExternalLink( $useUrl, $project, false );
 57+ }
 58+ if( $clickable ) {
 59+ $args['link-url'] = $useUrl;
 60+ } else {
 61+ $args['no-link'] = true;
 62+ }
 63+ $handlerParams['width'] = $width;
 64+ if( $height ) {
 65+ $handlerParams['height'] = $height;
 66+ }
 67+ return $wgUser->getSkin()->makeImageLink2( $this->mTitle, $imageobj,
 68+ array( 'alt' => $project, 'caption' => $project ) + $args, $handlerParams
 69+ );
 70+ }
 71+
 72+ public function listOtherProjects() {
 73+ global $wmincProjects, $wmincSisterProjects;
 74+ $otherProjects = $wmincProjects + $wmincSisterProjects;
 75+ foreach( $otherProjects as $code => $name ) {
 76+ $listOtherProjects[$code] = '<li>' . $this->makeLogo( $name, true,
 77+ 75, NULL, IncubatorTest::getSubdomain( $this->mLangCode, $name ) ) . '</li>';
 78+ }
 79+ unset($listOtherProjects[$this->mProjectCode]);
 80+ return '<ul class="wminc-infopage-otherprojects">' .
 81+ implode( '', $listOtherProjects ) . '</ul>';
 82+ }
 83+
 84+ public function listMultilingualProjects() {
 85+ global $wmincMultilingualProjects;
 86+ if( !is_array( $wmincMultilingualProjects ) ) { return; }
 87+ foreach($wmincMultilingualProjects as $url => $name) {
 88+ $list[$url] = '<li>' . $this->makeLogo( $name, true,
 89+ 75, NULL, 'http://'.$url.'/') . '</li>';
 90+ }
 91+ return '<ul class="wminc-infopage-multilingualprojects">' .
 92+ implode( '', $list ) . '</ul>';
 93+ }
 94+
 95+ public function showWelcome() {
 96+ return Html::rawElement( 'div', array( 'class' => 'wminc-infopage-welcome' ),
 97+ wfMsgWikiHtml( 'wminc-infopage-welcome' ) );
 98+ }
 99+
 100+ public function StandardInfoPage( $beforetitle, $aftertitle, $content ) {
 101+ global $wgLang, $wgOut;
 102+ $wgOut->addModules( 'WikimediaIncubator.InfoPage' );
 103+ return Html::rawElement( 'div', array( 'class' => 'wminc-infopage plainlinks',
 104+ 'lang' => $wgLang->getCode(), 'dir' => $wgLang->getDir() ),
 105+ $beforetitle .
 106+ Html::rawElement( 'div', array( 'class' => 'wminc-infopage-logo' ),
 107+ $this->makeLogo( $this->mProjectName, true, 175 )
 108+ ) .
 109+ Html::rawElement( 'div', array( 'class' => 'wminc-infopage-title' ),
 110+ wfMsg( 'wminc-infopage-title', $this->mProjectName, $this->mLangName ) .
 111+ $aftertitle ) .
 112+ $content );
 113+ }
 114+
 115+ public function showMissingWiki() {
 116+ $content = Html::rawElement( 'div',
 117+ array( 'class' => 'wminc-infopage-status' ),
 118+ wfMsgWikiHtml( 'wminc-infopage-missingwiki-text',
 119+ $this->mProjectName, $this->mLangName )
 120+ ) .
 121+ Html::rawElement( 'ul', array( 'class' => 'wminc-infopage-options' ),
 122+ Html::rawElement( 'li', null,
 123+ wfMsgExt( 'wminc-infopage-option-startwiki',
 124+ array( 'parseinline' ), $this->mProjectName ) ) .
 125+ Html::rawElement( 'li', null,
 126+ wfMsgExt( 'wminc-infopage-option-languages-existing',
 127+ array( 'parseinline' ), $this->mProjectName ) ) .
 128+ Html::rawElement( 'li', null,
 129+ wfMsgExt( 'wminc-infopage-option-sisterprojects-existing',
 130+ array( 'parseinline' ) ) . $this->listOtherProjects() ) .
 131+ Html::rawElement( 'li', null,
 132+ wfMsgExt( 'wminc-infopage-option-multilingual', array( 'parseinline' ) ) .
 133+ $this->listMultilingualProjects() )
 134+ );
 135+ return $this->StandardInfoPage( $this->showWelcome(), '', $content );
 136+ }
 137+
 138+ public function showIncubatingWiki() {
 139+ global $wgUser;
 140+ $bug = isset( $this->mBug ) ? $this->mBug : '';
 141+ if( $this->mThisLangData['type'] != 'invalid' ) {
 142+ $gotoMainPage = Html::rawElement( 'span',
 143+ array( 'class' => 'wminc-infopage-entertest' ),
 144+ '→ ' . $wgUser->getSkin()->link(
 145+ Title::newFromText( IncubatorTest::getMainPage( $this->mLangCode, $this->mPrefix ) ),
 146+ wfMsgNoTrans( 'wminc-infopage-enter' )
 147+ )
 148+ );
 149+ }
 150+ $subdomain = IncubatorTest::getSubdomain( $this->mLangCode, $this->mProjectName );
 151+ $subdomainLink = $wgUser->getSkin()->makeExternalLink( $subdomain, $subdomain );
 152+ $content = Html::rawElement( 'div', array( 'class' => 'wminc-infopage-status' ),
 153+ wfMsgWikiHtml( 'wminc-infopage-status-' . $this->mSubStatus, $subdomainLink ) );
 154+ if( $this->mSubStatus != 'approved' && $this->mThisLangData['type'] != 'invalid' ) {
 155+ $content .= Html::element( 'div',
 156+ array( 'class' => 'wminc-infopage-contribute' ),
 157+ wfMsg( 'wminc-infopage-contribute' ) );
 158+ }
 159+ return $this->StandardInfoPage( '', $gotoMainPage, $content );
 160+ }
 161+
 162+ public function showExistingWiki() {
 163+ global $wgLang, $wgUser;
 164+ $created = isset( $this->mCreated ) ? $this->mCreated : '';
 165+ $bug = isset( $this->mBug ) ? $this->mBug : '';
 166+ $subdomain = IncubatorTest::getSubdomain( $this->mLangCode, $this->mProjectName );
 167+ $subdomainLink = $wgUser->getSkin()->makeExternalLink( $subdomain, $subdomain );
 168+ if( $this->mThisLangData['type'] != 'invalid' ) {
 169+ $gotoSubdomain = Html::rawElement( 'span',
 170+ array( 'class' => 'wminc-infopage-entertest' ),
 171+ $wgLang->getArrow() . ' ' . $subdomainLink );
 172+ }
 173+ $content = Html::rawElement( 'div',
 174+ array( 'class' => 'wminc-infopage-status' ),
 175+ wfMsg( 'wminc-infopage-status-' . $this->mSubStatus, $subdomainLink )
 176+ ) . Html::rawElement( 'ul', array( 'class' => 'wminc-infopage-options' ),
 177+ Html::rawElement( 'li', null, wfMsgWikiHtml( 'wminc-infopage-option-sisterprojects-other' ) .
 178+ $this->listOtherProjects() ) .
 179+ Html::rawElement( 'li', null, wfMsgWikiHtml( 'wminc-infopage-option-multilingual' ) .
 180+ $this->listMultilingualProjects() )
 181+ );
 182+ return $this->StandardInfoPage( $this->showWelcome(), $gotoSubdomain, $content );
 183+ }
 184+}
\ No newline at end of file
Property changes on: trunk/extensions/WikimediaIncubator/InfoPage.php
___________________________________________________________________
Added: svn:eol-style
1185 + native
Index: trunk/extensions/WikimediaIncubator/WikimediaIncubator.i18n.php
@@ -11,29 +11,48 @@
1212 * @author SPQRobin
1313 */
1414 $messages['en'] = array(
 15+ # General messages
1516 'wminc-desc' => 'Test wiki system for Wikimedia Incubator',
16 - 'wminc-viewuserlang' => 'Look up user language and test wiki',
17 - 'wminc-viewuserlang-user' => 'Username:',
18 - 'wminc-viewuserlang-go' => 'Go',
19 - 'wminc-userdoesnotexist' => 'The user "$1" does not exist.',
 17+ 'wminc-manual' => 'Manual',
 18+ 'wminc-listwikis' => 'List of wikis',
2019 'wminc-testwiki' => 'Test wiki:',
2120 'wminc-testwiki-none' => 'None/All',
 21+ 'wminc-recentchanges-all' => 'All recent changes',
 22+ 'wminc-mainpage-url' => 'Main Page', # do not translate
 23+
 24+ # Preferences
2225 'wminc-prefinfo-language' => 'Your interface language - independent from your test wiki',
2326 'wminc-prefinfo-code' => 'The ISO 639 language code',
2427 'wminc-prefinfo-project' => 'Select the Wikimedia project (Incubator option is for users who do general work)',
2528 'wminc-prefinfo-error' => 'You selected a project that needs a language code.',
 29+
 30+ # Editing/creating pages errors
2631 'wminc-error-move-unprefixed' => "Error: The page you are trying to move to [[{{MediaWiki:Helppage}}|is unprefixed or has a wrong prefix]]!",
27 - 'wminc-error-wronglangcode' => "'''Error:''' The page you are trying to edit contains a [[{{MediaWiki:Helppage}}|wrong language code]] \"$1\"!",
28 - 'wminc-error-unprefixed' => "'''Error:''' The page you are trying to edit is [[{{MediaWiki:Helppage}}|unprefixed]]!",
29 - 'wminc-error-unprefixed-suggest' => "'''Error:''' The page you are trying to edit is [[{{MediaWiki:Helppage}}|unprefixed]]! You can create a page at [[:$1]].",
30 - 'right-viewuserlang' => 'View [[Special:ViewUserLang|user language and test wiki]]',
 32+ 'wminc-error-wronglangcode' => "'''Error:''' This page contains a [[{{MediaWiki:Helppage}}|wrong language code]] \"$1\"!",
 33+ 'wminc-error-unprefixed' => "'''Error:''' This page is [[{{MediaWiki:Helppage}}|unprefixed]]!",
 34+ 'wminc-error-unprefixed-suggest' => "'''Error:''' This page is [[{{MediaWiki:Helppage}}|unprefixed]]! You can create a page at [[:$1]].",
 35+ 'wminc-error-wiki-exists' => 'This wiki already exists. You can find this page on $1. If the wiki was recently created, please wait a few hours or days until all content is imported.',
 36+
 37+ # Special:RandomByTest
3138 'randombytest' => 'Random page by test wiki',
3239 'randombytest-nopages' => 'There are no pages in your test wiki, in the namespace: $1.',
33 - 'wminc-recentchanges-all' => 'All recent changes',
3440
 41+ # Special:ViewUserLang
 42+ 'wminc-viewuserlang' => 'Look up user language and test wiki',
 43+ 'wminc-viewuserlang-user' => 'Username:',
 44+ 'wminc-viewuserlang-go' => 'Go',
 45+ 'wminc-userdoesnotexist' => 'The user "$1" does not exist.',
 46+
 47+ # User groups
 48+ 'right-viewuserlang' => 'View [[Special:ViewUserLang|user language and test wiki]]',
3549 'group-test-sysop' => 'Test wiki administrators',
3650 'group-test-sysop-member' => 'test wiki administrator',
3751 'grouppage-test-sysop' => 'Project:Test wiki administrators',
 52+
 53+ # Language codes
 54+ 'wminc-code-macrolanguage' => 'The [[wikipedia:$2 language|"$3" language]] is a [[wikipedia:ISO 639 macrolanguage|macrolanguage]], consisting of the following member languages:',
 55+ 'wminc-code-collective' => 'The code "$1" does not refer to a specific language, but to a collection of languages, namely the [[w:$2 language|"$3" languages]].',
 56+ 'wminc-code-retired' => 'This language code has been changed and no longer refers to the original language.',
3857 );
3958
4059 /** Message documentation (Message documentation)

Sign-offs

UserFlagDate
Nikerabbitinspected08:46, 20 July 2011

Follow-up revisions

RevisionCommit summaryAuthorDate
r92567Add message file of r92559 to Translaterobin20:20, 19 July 2011
r92790Some documentation/syntax/whitespace fixes per Nikerabbit on r92559robin20:43, 21 July 2011
r92792Use Linker trick to get rid of wgUser, per r92559robin21:21, 21 July 2011
r94482Follow-up r92559:...robin22:17, 14 August 2011

Comments

#Comment by Nikerabbit (talk | contribs)   08:45, 20 July 2011

Is this register_globals vulnerability?

+$wmincClosedWikis = isset( $wgSiteMatrixClosedSites ) ? $wgSiteMatrixClosedSites : null;

That variable is always defined, why would it be undefined?

+               } elseif( !isset( $wmincExistingWikis ) || !is_array( $wmincExistingWikis ) ) {
$wgUser->getSkin()->

You can use the trick Dantman showed me. You can get rid of one global.

$linker = class_exists( 'DummyLinker' ) ? new DummyLinker : new Linker;

Could you document getSubdomain?

$params can be an array, no need to build it by appending to a string.

+$url = $mainpage->getFullURL( $params );

return as in return from the function or return some value (what?).

+# return if MediaWiki: Incubator-logo-wx/xx(x) does not exists

Please use !$file or $file === null, depending on which is appropriate.

+               if ( $file == null ) {

What is this rule for?

+#ca-nstab-main a {
+       color: black;
+}

In InfoPage.php there are some NULLs (should be lowercase) and missing whitespace. Could you also document the infopage messages (if not done already), thanks.

#Comment by SPQRobin (talk | contribs)   21:01, 21 July 2011

Most fixed in r92790.

As for the register_globals: outside of WMF it might be a vulnerability, but WMF defines $wgSiteMatrixClosedSites. Do you have a suggestion how I could fix it? Maybe define $wmincClosedWikis = false; and then configure it in Wikimedia to $wgSiteMatrixClosedSites (although I prefer to leave configuration in the extension itself :p).

The CSS rule is to make the tab black instead of red (a bit nicer).

#Comment by SPQRobin (talk | contribs)   00:07, 14 August 2011

$wmincClosedWikis set to false by default in r94434.

#Comment by Catrope (talk | contribs)   15:32, 14 August 2011
+$wmincScriptDir = $wgScriptPath . '/extensions/WikimediaIncubator/';

First, you should use $wgExtensionAssetsPath instead of $wgScriptPath when constructing paths to web-accessible extension resources.

+		'remoteExtPath' => $wmincScriptDir,

Second, remoteExtPath expects a path that is relative to $wgExtensionAssetsPath, so you should use 'remoteExtPath' => 'WikimediaIncubator'. Even though the setting is currently wrong, it won't break for you unless you use debug mode or use IE6/7 and use images in your CSS.

+			preg_match( '/^(' . implode( '|', $wmincPseudoCategoryNSes ) .'):.+$/', $title->getText() ) ) {

The entries in that array need to be escaped with preg_quote( $foo, '/' ) before they're stuck in a regex.

+				preg_replace( '/ /', '_', $prefixdata['realtitle'] ) );

Can be done with str_replace().

+		} elseif( !isset( $prefix ) || $prefix['error'] ) {

The isset() is useless here. Calling a function without a required (non-optional) parameter is unacceptable, period, you don't need to check for that. If you want the parameter to be optional, make it default to null and check for null instead.

+		return preg_replace('/-/', '_', $prefix['lang'] ) .

Can be done with str_replace().

+		return isset( $prefix ) ? $prefix . '/' . $msg : $msg;

Don't use isset( $prefix ) when what you really mean is !is_null( $prefix ) or $prefix !== null.

+		$prefixForPageTitle = preg_replace('/\//', '-', strtolower( $setLogo['prefix'] ) );

Can be done with str_replace().

+		$projectForFile = preg_replace('/ /', '-', strtolower( $project ) );

Can be done with str_replace().

+		$wgOut->addModules( 'WikimediaIncubator.InfoPage' );

Because your CSS applies to HTML that is generated by PHP, not by JS, use $wgOut->addModuleStyles() to avoid a flash of unstyled content.

+			Html::rawElement( 'div', array( 'class' => 'wminc-infopage-title' ),
+				wfMsg( 'wminc-infopage-title', $this->mProjectName, $this->mLangName ) .
+				$aftertitle ) .

There is no reason to use rawElement here, because the input is a message. Use element() so the text is escaped properly.

+		$created = isset( $this->mCreated ) ? $this->mCreated : '';
+		$bug = isset( $this->mBug ) ? $this->mBug : '';

??? Neither of these are referenced anywhere else.

+		$content = Html::rawElement( 'div',
+			array( 'class' => 'wminc-infopage-status' ),
+			wfMsg( 'wminc-infopage-status-' . $this->mSubStatus, $subdomainLink )

Again, don't use rawElement, use element so the message text is escaped properly.

#Comment by Catrope (talk | contribs)   15:36, 14 August 2011

Not introduced in this rev, but:

 		$listProjects =	implode( '', array_keys( $wmincProjects ) ); # something like: pbtqn
 		if( !preg_match( '/^W['.$listProjects.']\/[a-z-]+' .

This is a very dirty hack which assumes that $wmincProjects will always be an array of single-character strings that have no special meaning in regexes. A proper implementation would use implode( '|' , ... ) and would preg_quote() the elements before using them.

#Comment by SPQRobin (talk | contribs)   22:22, 14 August 2011

Things like preg_replace() -> str_replace() were already done in one of my recent commits. The rest should all have been addressed in r94482: As for the rawElement, that was not possible because the "a" tags would then be escaped, thus not forming the URL. Instead, I used wfMsgWikiHtml(). As for the $created and $bug, that's something intended for future use. Maybe should've left that out :) And for the addModuleStyles(): awesome! it's much better without the flash of unstyled content :-)

Status & tagging log