https://www.mediawiki.org/wiki/Special:Code/MediaWiki/112991
Revision: 112991
Author: krinkle
Date: 2012-03-04 23:56:25 +0000 (Sun, 04 Mar 2012)
Log Message:
-----------
[JSGrammar] Various minor tips, tricks and clean up.
* mediawiki.language.js:
-- Implement mw.language.getData and setData. This avoids having to repeat the
"if data[langCode] === undefined" code pattern all over the place (which in
practice often results in the check not being programmed or forgotten (such as
in mw.lang.convertGrammar)).
setData will initialize the object on-demand when needed.
getData will return 'undefined' if the object doesn't exist (whereas
mw.langauge.data[someCode].get would throw an exception if the object doesn't
exist)
-- Checking for $.isArray instead of thruthy-ness in convertPlural() and
gender(). When isolated a truth check could be sufficient (it would fail when
given a non-array thruthy value, but people simply shouldn't do that). However
since the second check compares.length === 0 it makes sense to be sure it's an
array first.
-- Create 'var language' as local object (for shortcut and slight performance
benefit), later exposing into mw.language
-- Remove redundant truthy check for 'mw.language.convertPlural', this is
defined the block below
-- Few comment fixes (var types, integer vs. Number in javascript)
-- Applying JS conventions
* ResourceLoaderLanguageModule
-- Rename module from 'language' to 'mediawiki.language.data'
-- Simplify ResourceLoaderLanguageModule::getScript
-- Add more elaborate FIXME note in
ResourceLoaderLanguageModule::getModifiedTime. I haven't figured out how to
properly cache and (more importantly) detect a change and purge the cache
automatically for a PHP global in a ResourceLoader JS module
Modified Paths:
--------------
branches/jsgrammar/includes/AutoLoader.php
branches/jsgrammar/resources/Resources.php
branches/jsgrammar/resources/mediawiki.language/mediawiki.language.js
branches/jsgrammar/tests/qunit/QUnitTestResources.php
Added Paths:
-----------
branches/jsgrammar/includes/resourceloader/ResourceLoaderLanguageDataModule.php
Removed Paths:
-------------
branches/jsgrammar/includes/resourceloader/ResourceLoaderLanguageModule.php
Modified: branches/jsgrammar/includes/AutoLoader.php
===================================================================
--- branches/jsgrammar/includes/AutoLoader.php 2012-03-04 23:51:41 UTC (rev
112990)
+++ branches/jsgrammar/includes/AutoLoader.php 2012-03-04 23:56:25 UTC (rev
112991)
@@ -732,7 +732,7 @@
'ResourceLoaderUserModule' =>
'includes/resourceloader/ResourceLoaderUserModule.php',
'ResourceLoaderUserOptionsModule' =>
'includes/resourceloader/ResourceLoaderUserOptionsModule.php',
'ResourceLoaderUserTokensModule' =>
'includes/resourceloader/ResourceLoaderUserTokensModule.php',
- 'ResourceLoaderLanguageModule' =>
'includes/resourceloader/ResourceLoaderLanguageModule.php',
+ 'ResourceLoaderLanguageDataModule' =>
'includes/resourceloader/ResourceLoaderLanguageDataModule.php',
'ResourceLoaderWikiModule' =>
'includes/resourceloader/ResourceLoaderWikiModule.php',
# includes/revisiondelete
Copied:
branches/jsgrammar/includes/resourceloader/ResourceLoaderLanguageDataModule.php
(from rev 112977,
branches/jsgrammar/includes/resourceloader/ResourceLoaderLanguageModule.php)
===================================================================
---
branches/jsgrammar/includes/resourceloader/ResourceLoaderLanguageDataModule.php
(rev 0)
+++
branches/jsgrammar/includes/resourceloader/ResourceLoaderLanguageDataModule.php
2012-03-04 23:56:25 UTC (rev 112991)
@@ -0,0 +1,86 @@
+<?php
+/**
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program; if not, write to the Free Software Foundation, Inc.,
+ * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ * http://www.gnu.org/copyleft/gpl.html
+ *
+ * @file
+ * @author Santhosh Thottingal
+ * @author Timo Tijhof
+ */
+
+/**
+ * ResourceLoader module for populating language specific data.
+ */
+class ResourceLoaderLanguageDataModule extends ResourceLoaderModule {
+
+ /**
+ * Get the grammer forms for the site content language.
+ *
+ * @return array
+ */
+ protected function getSiteLangGrammarForms() {
+ global $wgContLang;
+ return $wgContLang->getGrammarForms();
+ }
+
+ /**
+ * @param $context ResourceLoaderContext
+ * @return string Javascript code
+ */
+ public function getScript( ResourceLoaderContext $context ) {
+ global $wgContLang;
+
+ return Xml::encodeJsCall( 'mw.language.setData', array(
+ $wgContLang->getCode(),
+ $this->getSiteLangGrammarForms()
+ ) );
+ }
+
+ /**
+ * @param $context ResourceLoaderContext
+ * @return array|int|Mixed
+ */
+ public function getModifiedTime( ResourceLoaderContext $context ) {
+ global $wgCacheEpoch;
+
+ /**
+ * @todo FIXME: This needs to change whenever the array created
by
+ * $wgContLang->getGrammarForms() changes. Which gets its data
from
+ * $wgGrammarForms, which (for standard installations) comes
from LocalSettings
+ * and $wgCacheEpoch would cover that. However there's two
three problems:
+ *
+ * 1) $wgCacheEpoch is not meant for this use.
+ * 2) If $wgInvalidateCacheOnLocalSettingsChange is set to
false,
+ * $wgCacheEpoch will not be raised if LocalSettings is
modified (see #1).
+ * 3) $wgGrammarForms can be set from anywhere. For example on
WMF it is set
+ * by the WikimediaMessages extension. Other farms might set
it form
+ * their 'CommonSettings.php'-like file or something (see
#1).
+ *
+ * Possible solutions:
+ * - Store grammarforms in the language object cache instead of
directly
+ * from the global everytime. Then use
$wgContLang->getLastModified().
+ * - Somehow monitor the value of $wgGrammarForms.
+ */
+
+ return $wgCacheEpoch;
+ }
+
+ /**
+ * @return array
+ */
+ public function getDependencies() {
+ return array( 'mediawiki.language' );
+ }
+}
Deleted:
branches/jsgrammar/includes/resourceloader/ResourceLoaderLanguageModule.php
===================================================================
--- branches/jsgrammar/includes/resourceloader/ResourceLoaderLanguageModule.php
2012-03-04 23:51:41 UTC (rev 112990)
+++ branches/jsgrammar/includes/resourceloader/ResourceLoaderLanguageModule.php
2012-03-04 23:56:25 UTC (rev 112991)
@@ -1,78 +0,0 @@
-<?php
-/**
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; either version 2 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License along
- * with this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- * http://www.gnu.org/copyleft/gpl.html
- *
- * @file
- * @author Santhosh Thottingal
- * @author Timo Tijhof
- */
-
-/**
- * ResourceLoader module for generating language specific scripts/css.
- */
-class ResourceLoaderLanguageModule extends ResourceLoaderModule {
-
- /**
- * Get the grammer forms for the site content language.
- *
- * @return Array
- */
- protected function getSiteLangGrammarForms() {
- global $wgContLang;
- return $wgContLang->getGrammarForms();
- }
- /**
- * @param $context ResourceLoaderContext
- * @return string Javascript code
- */
- public function getScript( ResourceLoaderContext $context ) {
- global $wgContLang;
- $code = Xml::encodeJsVar( $wgContLang->getCode() );
- $forms = Xml::encodeJsVar( $this->getSiteLangGrammarForms() );
-
- $js =
-<<<JAVASCRIPT
-var langCode = $code,
-langData = mw.language.data;
-if ( langData[langCode] === undefined ) {
- langData[langCode] = new mw.Map();
-}
-langData[langCode].set( "grammarForms", $forms );
-JAVASCRIPT;
-
- return $js;
- }
- /**
- * @param $context ResourceLoaderContext
- * @return array|int|Mixed
- */
- public function getModifiedTime( ResourceLoaderContext $context ) {
- global $wgCacheEpoch;
- /*
- global $wgContLang, $wgCacheEpoch;
- return max( $wgCacheEpoch, $wgContLang->getLastModified() );
- */
-
- return $wgCacheEpoch;
- }
- /**
- * @return array
- */
- public function getDependencies() {
- return array( 'mediawiki.language' );
- }
-}
-
Modified: branches/jsgrammar/resources/Resources.php
===================================================================
--- branches/jsgrammar/resources/Resources.php 2012-03-04 23:51:41 UTC (rev
112990)
+++ branches/jsgrammar/resources/Resources.php 2012-03-04 23:56:25 UTC (rev
112991)
@@ -12,8 +12,8 @@
'user.options' => array( 'class' => 'ResourceLoaderUserOptionsModule' ),
'user.cssprefs' => array( 'class' => 'ResourceLoaderUserCSSPrefsModule'
),
'user.tokens' => array( 'class' => 'ResourceLoaderUserTokensModule' ),
- 'language' => array( 'class' => 'ResourceLoaderLanguageModule' ),
'filepage' => array( 'class' => 'ResourceLoaderFilePageModule' ),
+ 'mediawiki.language.data' => array( 'class' =>
'ResourceLoaderLanguageDataModule' ),
/* Skins */
Modified: branches/jsgrammar/resources/mediawiki.language/mediawiki.language.js
===================================================================
--- branches/jsgrammar/resources/mediawiki.language/mediawiki.language.js
2012-03-04 23:51:41 UTC (rev 112990)
+++ branches/jsgrammar/resources/mediawiki.language/mediawiki.language.js
2012-03-04 23:56:25 UTC (rev 112991)
@@ -5,48 +5,78 @@
* Language.php in MediaWiki. This object contains methods for loading and
* transforming message text.
*/
-( function( $, mw ) {
+( function ( $, mw ) {
-mw.language = {
+var language = {
/**
- * @var data {Object} Language related data
- * Keyed by language, contains instances of mw.Map
- * @example Set data
- * <code>
- * var langCode = 'nl';
- * var langData = mw.language.data;
- * if ( langData[langCode] === undefined ) {
- * langData[langCode] = new mw.Map();
- * }
- * langData[langCode].set( .. ); // Will override, extend or create the
data
- * </code>
- * @example Get data
- * <code>
- * var grammarForms = mw.language.data[langCode].get( 'grammarForms' );
- * </code>
- */
+ * @var data {Object} Language related data (keyed by language,
+ * contains instances of mw.Map).
+ * @example Set data
+ * <code>
+ * // Override, extend or create the language data object of 'nl'
+ * mw.language.setData( 'nl', 'myKey', 'My value' );
+ * </code>
+ * @example Get GrammarForms data for language 'nl':
+ * <code>
+ * var grammarForms = mw.language.getData( 'nl', 'grammarForms' );
+ * </code>
+ */
data: {},
+
/**
+ * Convenience method for retreiving language data by language code and
data key,
+ * covering for the potential inexistance of a data object for this
langiage.
+ * @param langCode {String}
+ * @param dataKey {String}
+ * @return {mixed} Value stored in the mw.Map (or undefined if there is
no map for
+ the specified langCode).
+ */
+ getData: function ( langCode, dataKey ) {
+ var langData = language.data;
+ if ( langData[langCode] instanceof mw.Map ) {
+ return langData[langCode].get( dataKey );
+ }
+ return undefined;
+ },
+
+ /**
+ * Convenience method for setting language data by language code and
data key.
+ * Creates a data object if there isn't one for the specified language
already.
+ * @param langCode {String}
+ * @param dataKey {String}
+ * @param value {mixed}
+ */
+ setData: function ( langCode, dataKey, value ) {
+ var langData = language.data;
+ if ( !( langData[langCode] instanceof mw.Map ) ) {
+ langData[langCode] = new mw.Map();
+ }
+ langData[langCode].set( dataKey, value );
+ },
+
+ /**
* Process the PLURAL template substitution
*
- * @param {object} template Template object
+ * @param template {Object} Template object
* @format template
- * {
- * 'title': [title of template],
- * 'parameters': [template parameters]
- * }
+ * {
+ * title: [title of template],
+ * parameters: [template parameters]
+ * }
* @example {{Template:title|params}}
*/
- procPLURAL: function( template ) {
- if ( template.title && template.parameters &&
mw.language.convertPlural ) {
+ procPLURAL: function ( template ) {
+ var count;
+
+ if ( template.title && template.parameters ) {
// Check if we have forms to replace
if ( template.parameters.length === 0 ) {
return '';
}
// Restore the count into a Number ( if it got
converted earlier )
- var count = mw.language.convertNumber( template.title,
true );
+ count = language.convertNumber( template.title, true );
// Do convertPlural call
- return mw.language.convertPlural( parseInt( count, 10
), template.parameters );
+ return language.convertPlural( parseInt( count, 10 ),
template.parameters );
}
// Could not process plural return first form or nothing
if ( template.parameters[0] ) {
@@ -54,25 +84,27 @@
}
return '';
},
+
/**
* Plural form transformations, needed for some languages.
*
- * @param count integer Non-localized quantifier
- * @param forms array List of plural forms
- * @return string Correct form for quantifier in this language
+ * @param count {Number} Non-localized quantifier
+ * @param forms {Array} List of plural forms
+ * @return {String} Correct form for quantifier in this language
*/
- convertPlural: function( count, forms ){
- if ( !forms || forms.length === 0 ) {
+ convertPlural: function ( count, forms ){
+ if ( !$.isArray( forms ) || forms.length === 0 ) {
return '';
}
- return ( parseInt( count, 10 ) == 1 ) ? forms[0] : forms[1];
+ return ( parseInt( count, 10 ) === 1 ) ? forms[0] : forms[1];
},
+
/**
* Pads an array to a specific length by copying the last one element.
*
- * @param forms array Number of forms given to convertPlural
- * @param count integer Number of forms required
- * @return array Padded array of forms
+ * @param forms {Array} List of forms given to convertPlural
+ * @param count {Number} Number of forms required
+ * @return {Array} Padded array of forms
*/
preConvertPlural: function( forms, count ) {
while ( forms.length < count ) {
@@ -80,32 +112,35 @@
}
return forms;
},
+
/**
* Converts a number using digitTransformTable.
*
- * @param {num} number Value to be converted
- * @param {boolean} integer Convert the return value to an integer
+ * @param num {Number} Value to be converted
+ * @param integer {Boolean} Convert the return value to an integer
*/
convertNumber: function( num, integer ) {
- if ( !mw.language.digitTransformTable ) {
+ var transformTable, tmp, i, numberString, convertedNumber;
+
+ if ( !language.digitTransformTable ) {
return num;
}
// Set the target Transform table:
- var transformTable = mw.language.digitTransformTable;
+ transformTable = language.digitTransformTable;
// Check if the "restore" to Latin number flag is set:
if ( integer ) {
- if ( parseInt( num, 10 ) == num ) {
+ if ( parseInt( num, 10 ) === num ) {
return num;
}
- var tmp = [];
- for ( var i in transformTable ) {
+ tmp = [];
+ for ( i in transformTable ) {
tmp[ transformTable[ i ] ] = i;
}
transformTable = tmp;
}
- var numberString = '' + num;
- var convertedNumber = '';
- for ( var i = 0; i < numberString.length; i++ ) {
+ numberString = String( num );
+ convertedNumber = '';
+ for ( i = 0; i < numberString.length; i++ ) {
if ( transformTable[ numberString[i] ] ) {
convertedNumber +=
transformTable[numberString[i]];
} else {
@@ -114,6 +149,7 @@
}
return integer ? parseInt( convertedNumber, 10 ) :
convertedNumber;
},
+
/**
* Provides an alternative text depending on specified gender.
* Usage {{gender:[gender|user object]|masculine|feminine|neutral}}.
@@ -121,16 +157,17 @@
*
* These details may be overriden per language.
*
- * @param gender string male, female, or anything else for neutral.
- * @param forms array List of gender forms
+ * @param gender {String} Male, female, or anything else for neutral.
+ * @param forms {Array} List of gender forms
*
- * @return string
+ * @return {String}
*/
- gender: function( gender, forms ) {
- if ( !forms || forms.length === 0 ) {
+
+ gender: function ( gender, forms ) {
+ if ( !$.isArray( forms ) || forms.length === 0 ) {
return '';
}
- forms = mw.language.preConvertPlural( forms, 2 );
+ forms = language.preConvertPlural( forms, 2 );
if ( gender === 'male' ) {
return forms[0];
}
@@ -139,24 +176,31 @@
}
return ( forms.length === 3 ) ? forms[2] : forms[0];
},
+
/**
* Grammatical transformations, needed for inflected languages.
* Invoked by putting {{grammar:form|word}} in a message.
- * The rules can be defined in wgGrammarForms global or grammar
+ * The rules can be defined in $wgGrammarForms global or grammar
* forms can be computed dynamically by overriding this method per
language
*
- * @param word string
- * @param form string
- * @return string
+ * @param word {String}
+ * @param form {String}
+ * @return {String}
*/
- convertGrammar: function( word, form ) {
- var grammarForms = mw.language.data[mw.config.get(
'wgContentLanguage' )].get( 'grammarForms' );
+ convertGrammar: function ( word, form ) {
+ var grammarForms = language.getData( mw.config.get(
'wgContentLanguage' ), 'grammarForms' );
if ( grammarForms && grammarForms[form] ) {
return grammarForms[form][word] || word;
}
return word;
},
- // Digit Transform Table, populated by language classes where applicable
+
+ /**
+ * @var {Object} Digit Transform Table, populated by language classes
where applicable.
+ */
digitTransformTable: null
};
-} )( jQuery, mediaWiki );
+
+mw.language = language;
+
+}( jQuery, mediaWiki ) );
Modified: branches/jsgrammar/tests/qunit/QUnitTestResources.php
===================================================================
--- branches/jsgrammar/tests/qunit/QUnitTestResources.php 2012-03-04
23:51:41 UTC (rev 112990)
+++ branches/jsgrammar/tests/qunit/QUnitTestResources.php 2012-03-04
23:56:25 UTC (rev 112991)
@@ -25,8 +25,8 @@
'tests/qunit/suites/resources/mediawiki/mediawiki.user.test.js',
'tests/qunit/suites/resources/mediawiki/mediawiki.util.test.js',
'tests/qunit/suites/resources/mediawiki.special/mediawiki.special.recentchanges.test.js',
-
"tests/qunit/suites/resources/mediawiki/mediawiki.jqueryMsg.test.js",
-
"tests/qunit/suites/resources/mediawiki/mediawiki.language.test.js",
+
'tests/qunit/suites/resources/mediawiki/mediawiki.jqueryMsg.test.js',
+
'tests/qunit/suites/resources/mediawiki/mediawiki.language.test.js',
),
'dependencies' => array(
'jquery.autoEllipsis',
@@ -43,7 +43,7 @@
'jquery.tablesorter',
'jquery.textSelection',
'mediawiki',
- 'language',
+ 'mediawiki.language.data',
'mediawiki.Title',
'mediawiki.user',
'mediawiki.util',
_______________________________________________
MediaWiki-CVS mailing list
[email protected]
https://lists.wikimedia.org/mailman/listinfo/mediawiki-cvs