resourceloader: Add support for delivering templates
[lhc/web/wiklou.git] / includes / resourceloader / ResourceLoaderFileModule.php
index 137ff62..d4e8159 100644 (file)
@@ -34,6 +34,9 @@ class ResourceLoaderFileModule extends ResourceLoaderModule {
        /** @var string Remote base path, see __construct() */
        protected $remoteBasePath = '';
 
+       /** @var array Saves a list of the templates named by the modules. */
+       protected $templates = array();
+
        /**
         * @var array List of paths to JavaScript files to always include
         * @par Usage:
@@ -199,6 +202,9 @@ class ResourceLoaderFileModule extends ResourceLoaderModule {
         *         'loaderScripts' => [file path string or array of file path strings],
         *         // Modules which must be loaded before this module
         *         'dependencies' => [module name string or array of module name strings],
+        *         'templates' => array(
+        *             [template alias with file.ext] => [file path to a template file],
+        *         ),
         *         // Styles to always load
         *         'styles' => [file path string or array of file path strings],
         *         // Styles to include in specific skin contexts
@@ -223,6 +229,8 @@ class ResourceLoaderFileModule extends ResourceLoaderModule {
                $localBasePath = null,
                $remoteBasePath = null
        ) {
+               // Flag to decide whether to automagically add the mediawiki.template module
+               $hasTemplates = false;
                // localBasePath and remoteBasePath both have unbelievably long fallback chains
                // and need to be handled separately.
                list( $this->localBasePath, $this->remoteBasePath ) =
@@ -238,6 +246,10 @@ class ResourceLoaderFileModule extends ResourceLoaderModule {
                                case 'styles':
                                        $this->{$member} = (array)$option;
                                        break;
+                               case 'templates':
+                                       $hasTemplates = true;
+                                       $this->{$member} = (array)$option;
+                                       break;
                                // Collated lists of file paths
                                case 'languageScripts':
                                case 'skinScripts':
@@ -281,6 +293,9 @@ class ResourceLoaderFileModule extends ResourceLoaderModule {
                                        break;
                        }
                }
+               if ( $hasTemplates ) {
+                       $this->dependencies[] = 'mediawiki.template';
+               }
        }
 
        /**
@@ -304,7 +319,9 @@ class ResourceLoaderFileModule extends ResourceLoaderModule {
                // The different ways these checks are done, and their ordering, look very silly,
                // but were preserved for backwards-compatibility just in case. Tread lightly.
 
-               $localBasePath = $localBasePath === null ? $IP : $localBasePath;
+               if ( $localBasePath === null ) {
+                       $localBasePath = $IP;
+               }
                if ( $remoteBasePath === null ) {
                        $remoteBasePath = $wgResourceBasePath;
                }
@@ -533,8 +550,9 @@ class ResourceLoaderFileModule extends ResourceLoaderModule {
                $files = array_merge(
                        $files,
                        $this->scripts,
+                       $this->templates,
                        $context->getDebug() ? $this->debugScripts : array(),
-                       self::tryForKey( $this->languageScripts, $context->getLanguage() ),
+                       $this->getLanguageScripts( $context->getLanguage() ),
                        self::tryForKey( $this->skinScripts, $context->getSkin(), 'default' ),
                        $this->loaderScripts
                );
@@ -588,6 +606,7 @@ class ResourceLoaderFileModule extends ResourceLoaderModule {
                        'dependencies',
                        'messages',
                        'targets',
+                       'templates',
                        'group',
                        'position',
                        'skipFunction',
@@ -698,7 +717,7 @@ class ResourceLoaderFileModule extends ResourceLoaderModule {
        protected function getScriptFiles( ResourceLoaderContext $context ) {
                $files = array_merge(
                        $this->scripts,
-                       self::tryForKey( $this->languageScripts, $context->getLanguage() ),
+                       $this->getLanguageScripts( $context->getLanguage() ),
                        self::tryForKey( $this->skinScripts, $context->getSkin(), 'default' )
                );
                if ( $context->getDebug() ) {
@@ -708,6 +727,29 @@ class ResourceLoaderFileModule extends ResourceLoaderModule {
                return array_unique( $files, SORT_REGULAR );
        }
 
+       /**
+        * Get the set of language scripts for the given language,
+        * possibly using a fallback language.
+        *
+        * @param string $lang
+        * @return array
+        */
+       private function getLanguageScripts( $lang ) {
+               $scripts = self::tryForKey( $this->languageScripts, $lang );
+               if ( $scripts ) {
+                       return $scripts;
+               }
+               $fallbacks = Language::getFallbacksFor( $lang );
+               foreach ( $fallbacks as $lang ) {
+                       $scripts = self::tryForKey( $this->languageScripts, $lang );
+                       if ( $scripts ) {
+                               return $scripts;
+                       }
+               }
+
+               return array();
+       }
+
        /**
         * Get a list of file paths for all styles in this module, in order of proper inclusion.
         *
@@ -870,8 +912,6 @@ class ResourceLoaderFileModule extends ResourceLoaderModule {
 
                if ( $flip ) {
                        $style = CSSJanus::transform( $style, true, false );
-               } else {
-                       $style = CSSJanus::nullTransform( $style );
                }
                $localDir = dirname( $localPath );
                $remoteDir = dirname( $remotePath );
@@ -936,4 +976,30 @@ class ResourceLoaderFileModule extends ResourceLoaderModule {
        protected function getLessCompiler( ResourceLoaderContext $context = null ) {
                return ResourceLoader::getLessCompiler( $this->getConfig() );
        }
+
+       /**
+        * Takes named templates by the module and returns an array mapping.
+        *
+        * @return array of templates mapping template alias to content
+        */
+       public function getTemplates() {
+               $templates = array();
+
+               foreach ( $this->templates as $alias => $templatePath ) {
+                       // Alias is optional
+                       if ( is_int( $alias ) ) {
+                               $alias = $templatePath;
+                       }
+                       $localPath = $this->getLocalPath( $templatePath );
+                       if ( file_exists( $localPath ) ) {
+                               $content = file_get_contents( $localPath );
+                               $templates[ $alias ] = $content;
+                       } else {
+                               $msg = __METHOD__ . ": template file not found: \"$localPath\"";
+                               wfDebugLog( 'resourceloader', $msg );
+                               throw new MWException( $msg );
+                       }
+               }
+               return $templates;
+       }
 }