Made ResourceLoader an instantiable object, rather than a static one, making it more...
authorTrevor Parscal <tparscal@users.mediawiki.org>
Wed, 29 Sep 2010 19:04:04 +0000 (19:04 +0000)
committerTrevor Parscal <tparscal@users.mediawiki.org>
Wed, 29 Sep 2010 19:04:04 +0000 (19:04 +0000)
includes/MessageBlobStore.php
includes/OutputPage.php
includes/ResourceLoader.php
includes/ResourceLoaderContext.php
includes/ResourceLoaderModule.php
load.php
maintenance/tests/phpunit/includes/ResourceLoaderTest.php

index 45a8b27..604b1d4 100644 (file)
@@ -31,7 +31,7 @@
 class MessageBlobStore {
        /**
         * Get the message blobs for a set of modules
-        * @param $modules array Array of module names
+        * @param $modules array Array of module objects keyed by module name
         * @param $lang string Language code
         * @return array An array mapping module names to message blobs
         */
@@ -43,14 +43,14 @@ class MessageBlobStore {
                        return array();
                }
                // Try getting from the DB first
-               $blobs = self::getFromDB( $modules, $lang );
+               $blobs = self::getFromDB( array_keys( $modules ), $lang );
 
                // Generate blobs for any missing modules and store them in the DB
-               $missing = array_diff( $modules, array_keys( $blobs ) );
-               foreach ( $missing as $module ) {
-                       $blob = self::insertMessageBlob( $module, $lang );
+               $missing = array_diff( array_keys( $modules ), array_keys( $blobs ) );
+               foreach ( $missing as $name ) {
+                       $blob = self::insertMessageBlob( $name, $modules[$name], $lang );
                        if ( $blob ) {
-                               $blobs[$module] = $blob;
+                               $blobs[$name] = $blob;
                        }
                }
 
@@ -66,8 +66,8 @@ class MessageBlobStore {
         * @param $lang string Language code
         * @return mixed Message blob or false if the module has no messages
         */
-       public static function insertMessageBlob( $module, $lang ) {
-               $blob = self::generateMessageBlob( $module, $lang );
+       public static function insertMessageBlob( $name, ResourceLoaderModule $module, $lang ) {
+               $blob = self::generateMessageBlob( $name, $module, $lang );
 
                if ( !$blob ) {
                        return false;
@@ -76,7 +76,7 @@ class MessageBlobStore {
                $dbw = wfGetDB( DB_MASTER );
                $success = $dbw->insert( 'msg_resource', array(
                                'mr_lang' => $lang,
-                               'mr_resource' => $module,
+                               'mr_resource' => $name,
                                'mr_blob' => $blob,
                                'mr_timestamp' => $dbw->timestamp()
                        ),
@@ -88,7 +88,7 @@ class MessageBlobStore {
                        if ( $dbw->affectedRows() == 0 ) {
                                // Blob was already present, fetch it
                                $blob = $dbw->selectField( 'msg_resource', 'mr_blob', array(
-                                               'mr_resource' => $module,
+                                               'mr_resource' => $name,
                                                'mr_lang' => $lang,
                                        ),
                                        __METHOD__
@@ -96,11 +96,10 @@ class MessageBlobStore {
                        } else {
                                // Update msg_resource_links
                                $rows = array();
-                               $mod = ResourceLoader::getModule( $module );
 
-                               foreach ( $mod->getMessages() as $key ) {
+                               foreach ( $module->getMessages() as $key ) {
                                        $rows[] = array(
-                                               'mrl_resource' => $module,
+                                               'mrl_resource' => $name,
                                                'mrl_message' => $key
                                        );
                                }
@@ -120,14 +119,14 @@ class MessageBlobStore {
         * @return mixed If $lang is set, the new message blob for that language is 
         *    returned if present. Otherwise, null is returned.
         */
-       public static function updateModule( $module, $lang = null ) {
+       public static function updateModule( $name, ResourceLoaderModule $module, $lang = null ) {
                $retval = null;
 
                // Find all existing blobs for this module
                $dbw = wfGetDB( DB_MASTER );
                $res = $dbw->select( 'msg_resource',
                        array( 'mr_lang', 'mr_blob' ),
-                       array( 'mr_resource' => $module ),
+                       array( 'mr_resource' => $name ),
                        __METHOD__
                );
 
@@ -139,13 +138,13 @@ class MessageBlobStore {
 
                foreach ( $res as $row ) {
                        $oldBlob = $row->mr_blob;
-                       $newBlob = self::generateMessageBlob( $module, $row->mr_lang );
+                       $newBlob = self::generateMessageBlob( $name, $module, $row->mr_lang );
 
                        if ( $row->mr_lang === $lang ) {
                                $retval = $newBlob;
                        }
                        $newRows[] = array(
-                               'mr_resource' => $module,
+                               'mr_resource' => $name,
                                'mr_lang' => $row->mr_lang,
                                'mr_blob' => $newBlob,
                                'mr_timestamp' => $now
@@ -166,7 +165,7 @@ class MessageBlobStore {
                // Delete removed messages, insert added ones
                if ( $removed ) {
                        $dbw->delete( 'msg_resource_links', array(
-                                       'mrl_resource' => $module,
+                                       'mrl_resource' => $name,
                                        'mrl_message' => $removed
                                ), __METHOD__
                        );
@@ -176,7 +175,7 @@ class MessageBlobStore {
 
                foreach ( $added as $message ) {
                        $newLinksRows[] = array(
-                               'mrl_resource' => $module,
+                               'mrl_resource' => $name,
                                'mrl_message' => $message
                        );
                }
@@ -343,11 +342,10 @@ class MessageBlobStore {
         * @param $lang string Language code
         * @return string JSON object
         */
-       private static function generateMessageBlob( $module, $lang ) {
-               $mod = ResourceLoader::getModule( $module );
+       private static function generateMessageBlob( $name, ResourceLoaderModule $module, $lang ) {
                $messages = array();
 
-               foreach ( $mod->getMessages() as $key ) {
+               foreach ( $module->getMessages() as $key ) {
                        $messages[$key] = wfMsgExt( $key, array( 'language' => $lang ) );
                }
 
index a32b04e..94edee8 100644 (file)
@@ -25,6 +25,7 @@ class OutputPage {
 
        var $mScripts = '', $mLinkColours, $mPageLinkTitle = '', $mHeadItems = array();
        var $mModules = array(), $mModuleScripts = array(), $mModuleStyles = array(), $mModuleMessages = array();
+       var $mResourceLoader;
        var $mInlineMsg = array();
 
        var $mTemplateIds = array();
@@ -2281,9 +2282,13 @@ class OutputPage {
        }
        
        // TODO: Document
-       static function makeResourceLoaderLink( $skin, $modules, $only, $useESI = false ) {
+       protected function makeResourceLoaderLink( $skin, $modules, $only, $useESI = false ) {
                global $wgUser, $wgLang, $wgRequest, $wgLoadScript, $wgResourceLoaderDebug, $wgResourceLoaderUseESI,
                        $wgResourceLoaderInlinePrivateModules;
+               // Lazy-load ResourceLoader
+               if ( is_null( $this->mResourceLoader ) ) {
+                       $this->mResourceLoader = new ResourceLoader();
+               }
                // TODO: Should this be a static function of ResourceLoader instead?
                // TODO: Divide off modules starting with "user", and add the user parameter to them
                $query = array(
@@ -2299,7 +2304,7 @@ class OutputPage {
                // Create keyed-by-group list of module objects from modules list
                $groups = array();
                foreach ( (array) $modules as $name ) {
-                       $module = ResourceLoader::getModule( $name );
+                       $module = $this->mResourceLoader->getModule( $name );
                        $group = $module->getGroup();
                        if ( !isset( $groups[$group] ) ) {
                                $groups[$group] = array();
@@ -2315,17 +2320,17 @@ class OutputPage {
                        }
                        // Support inlining of private modules if configured as such
                        if ( $group === 'private' && $wgResourceLoaderInlinePrivateModules ) {
-                               $context = new ResourceLoaderContext( new FauxRequest( $query ) );
+                               $context = new ResourceLoaderContext( $this->mResourceLoader, new FauxRequest( $query ) );
                                if ( $only == 'styles' ) {
                                        $links .= Html::inlineStyle(
                                                ResourceLoader::makeLoaderConditionalScript(
-                                                       ResourceLoader::makeModuleResponse( $context, $modules )
+                                                       $this->mResourceLoader->makeModuleResponse( $context, $modules )
                                                )
                                        );
                                } else {
                                        $links .= Html::inlineScript(
                                                ResourceLoader::makeLoaderConditionalScript(
-                                                       ResourceLoader::makeModuleResponse( $context, $modules )
+                                                       $this->mResourceLoader->makeModuleResponse( $context, $modules )
                                                )
                                        );
                                }
@@ -2336,7 +2341,7 @@ class OutputPage {
                        // we can ensure cache misses on change
                        if ( $group === 'user' || $group === 'site' ) {
                                // Create a fake request based on the one we are about to make so modules return correct times
-                               $context = new ResourceLoaderContext( new FauxRequest( $query ) );
+                               $context = new ResourceLoaderContext( $this->mResourceLoader, new FauxRequest( $query ) );
                                // Get the maximum timestamp
                                $timestamp = 0;
                                foreach ( $modules as $module ) {
@@ -2380,7 +2385,7 @@ class OutputPage {
                global $wgUser, $wgRequest, $wgUseSiteJs, $wgResourceLoaderDebug;
                
                // Startup - this will immediately load jquery and mediawiki modules
-               $scripts = self::makeResourceLoaderLink( $sk, 'startup', 'scripts', true );
+               $scripts = $this->makeResourceLoaderLink( $sk, 'startup', 'scripts', true );
                
                // Configuration -- This could be merged together with the load and go, but makeGlobalVariablesScript returns a
                // whole script tag -- grumble grumble...
@@ -2390,20 +2395,20 @@ class OutputPage {
                if ( $wgRequest->getFuzzyBool( 'debug', $wgResourceLoaderDebug ) ) {
                        // Scripts
                        foreach ( $this->getModuleScripts() as $name ) {
-                               $scripts .= self::makeResourceLoaderLink( $sk, $name, 'scripts' );
+                               $scripts .= $this->makeResourceLoaderLink( $sk, $name, 'scripts' );
                        }
                        // Messages
                        foreach ( $this->getModuleMessages() as $name ) {
-                               $scripts .= self::makeResourceLoaderLink( $sk, $name, 'messages' );
+                               $scripts .= $this->makeResourceLoaderLink( $sk, $name, 'messages' );
                        }
                } else {
                        // Scripts
                        if ( count( $this->getModuleScripts() ) ) {
-                               $scripts .= self::makeResourceLoaderLink( $sk, $this->getModuleScripts(), 'scripts' );
+                               $scripts .= $this->makeResourceLoaderLink( $sk, $this->getModuleScripts(), 'scripts' );
                        }
                        // Messages
                        if ( count( $this->getModuleMessages() ) ) {
-                               $scripts .= self::makeResourceLoaderLink( $sk, $this->getModuleMessages(), 'messages' );
+                               $scripts .= $this->makeResourceLoaderLink( $sk, $this->getModuleMessages(), 'messages' );
                        }
                }
                
@@ -2423,18 +2428,18 @@ class OutputPage {
                                # XXX: additional security check/prompt?
                                $this->addInlineScript( $wgRequest->getText( 'wpTextbox1' ) );
                        } else {
-                               $scripts .= self::makeResourceLoaderLink( $sk, array( 'user', 'user.options' ), 'scripts' );
+                               $scripts .= $this->makeResourceLoaderLink( $sk, array( 'user', 'user.options' ), 'scripts' );
                                $userOptionsAdded = true;
                        }
                }
                if ( !$userOptionsAdded ) {
-                       $scripts .= self::makeResourceLoaderLink( $sk, 'user.options', 'scripts' );
+                       $scripts .= $this->makeResourceLoaderLink( $sk, 'user.options', 'scripts' );
                }
                $scripts .= "\n" . $this->mScripts;
                
                // Add site JS if enabled
                if ( $wgUseSiteJs ) {
-                       $scripts .= self::makeResourceLoaderLink( $sk, 'site', 'scripts' );
+                       $scripts .= $this->makeResourceLoaderLink( $sk, 'site', 'scripts' );
                }
                
                return $scripts;
@@ -2558,11 +2563,11 @@ class OutputPage {
                // Support individual script requests in debug mode
                if ( $wgRequest->getFuzzyBool( 'debug', $wgResourceLoaderDebug ) ) {
                        foreach ( $this->getModuleStyles() as $name ) {
-                               $tags[] = self::makeResourceLoaderLink( $sk, $name, 'styles' );
+                               $tags[] = $this->makeResourceLoaderLink( $sk, $name, 'styles' );
                        }
                } else {
                        if ( count( $this->getModuleStyles() ) ) {
-                               $tags[] = self::makeResourceLoaderLink( $sk, $this->getModuleStyles(), 'styles' );
+                               $tags[] = $this->makeResourceLoaderLink( $sk, $this->getModuleStyles(), 'styles' );
                        }
                }
                
index 5647f69..1f2538b 100644 (file)
@@ -30,30 +30,11 @@ class ResourceLoader {
        /* Protected Static Members */
 
        // @var array list of module name/ResourceLoaderModule object pairs
-       protected static $modules = array();
-       protected static $initialized = false;
+       protected $modules = array();
 
-       /* Protected Static Methods */
-
-       /**
-        * Registers core modules and runs registration hooks
-        */
-       protected static function initialize() {
-               global $IP;
-               
-               // Safety check - this should never be called more than once
-               if ( !self::$initialized ) {
-                       wfProfileIn( __METHOD__ );
-                       // This needs to be first, because hooks might call ResourceLoader 
-                       // public interfaces which will call this
-                       self::$initialized = true;
-                       self::register( include( "$IP/resources/Resources.php" ) );
-                       wfRunHooks( 'ResourceLoaderRegisterModules' );
-                       wfProfileOut( __METHOD__ );
-               }
-       }
+       /* Protected Methods */
        
-       /*
+       /**
         * Loads information stored in the database about modules
         * 
         * This is not inside the module code because it's so much more performant to request all of the information at once
@@ -62,7 +43,7 @@ class ResourceLoader {
         * @param $modules array list of module names to preload information for
         * @param $context ResourceLoaderContext context to load the information within
         */
-       protected static function preloadModuleInfo( array $modules, ResourceLoaderContext $context ) {
+       protected function preloadModuleInfo( array $modules, ResourceLoaderContext $context ) {
                $dbr = wfGetDb( DB_SLAVE );
                $skin = $context->getSkin();
                $lang = $context->getLanguage();
@@ -76,21 +57,21 @@ class ResourceLoader {
                
                $modulesWithDeps = array();
                foreach ( $res as $row ) {
-                       self::$modules[$row->md_module]->setFileDependencies( $skin,
+                       $this->modules[$row->md_module]->setFileDependencies( $skin,
                                FormatJson::decode( $row->md_deps, true )
                        );
                        $modulesWithDeps[] = $row->md_module;
                }
                // Register the absence of a dependencies row too
                foreach ( array_diff( $modules, $modulesWithDeps ) as $name ) {
-                       self::$modules[$name]->setFileDependencies( $skin, array() );
+                       $this->modules[$name]->setFileDependencies( $skin, array() );
                }
                
                // Get message blob mtimes. Only do this for modules with messages
                $modulesWithMessages = array();
                $modulesWithoutMessages = array();
                foreach ( $modules as $name ) {
-                       if ( count( self::$modules[$name]->getMessages() ) ) {
+                       if ( count( $this->modules[$name]->getMessages() ) ) {
                                $modulesWithMessages[] = $name;
                        } else {
                                $modulesWithoutMessages[] = $name;
@@ -103,11 +84,11 @@ class ResourceLoader {
                                ), __METHOD__
                        );
                        foreach ( $res as $row ) {
-                               self::$modules[$row->mr_resource]->setMsgBlobMtime( $lang, $row->mr_timestamp );
+                               $this->modules[$row->mr_resource]->setMsgBlobMtime( $lang, $row->mr_timestamp );
                        }
                }
                foreach ( $modulesWithoutMessages as $name ) {
-                       self::$modules[$name]->setMsgBlobMtime( $lang, 0 );
+                       $this->modules[$name]->setMsgBlobMtime( $lang, 0 );
                }
        }
 
@@ -119,7 +100,7 @@ class ResourceLoader {
         * @param $file String: path to file being filtered, (optional: only required for CSS to resolve paths)
         * @return String: filtered data
         */
-       protected static function filter( $filter, $data ) {
+       protected function filter( $filter, $data ) {
                global $wgMemc;
                wfProfileIn( __METHOD__ );
 
@@ -166,7 +147,23 @@ class ResourceLoader {
                return $result;
        }
 
-       /* Static Methods */
+       /* Methods */
+
+       /**
+        * Registers core modules and runs registration hooks
+        */
+       public function __construct() {
+               global $IP;
+               
+               wfProfileIn( __METHOD__ );
+               
+               // Register core modules
+               $this->register( include( "$IP/resources/Resources.php" ) );
+               // Register extension modules
+               wfRunHooks( 'ResourceLoaderRegisterModules', array( &$this ) );
+               
+               wfProfileOut( __METHOD__ );
+       }
 
        /**
         * Registers a module with the ResourceLoader system.
@@ -184,14 +181,13 @@ class ResourceLoader {
         *    happened, but in bringing errors to the client in a way that they can 
         *    easily see them if they want to, such as by using FireBug
         */
-       public static function register( $name, ResourceLoaderModule $object = null ) {
+       public function register( $name, ResourceLoaderModule $object = null ) {
                wfProfileIn( __METHOD__ );
-               self::initialize();
                
                // Allow multiple modules to be registered in one call
                if ( is_array( $name ) && !isset( $object ) ) {
                        foreach ( $name as $key => $value ) {
-                               self::register( $key, $value );
+                               $this->register( $key, $value );
                        }
 
                        wfProfileOut( __METHOD__ );
@@ -199,13 +195,14 @@ class ResourceLoader {
                }
 
                // Disallow duplicate registrations
-               if ( isset( self::$modules[$name] ) ) {
+               if ( isset( $this->modules[$name] ) ) {
                        // A module has already been registered by this name
                        throw new MWException( 'Another module has already been registered as ' . $name );
                }
                // Attach module
-               self::$modules[$name] = $object;
+               $this->modules[$name] = $object;
                $object->setName( $name );
+               
                wfProfileOut( __METHOD__ );
        }
 
@@ -214,11 +211,8 @@ class ResourceLoader {
         *
         * @return Array: array( modulename => ResourceLoaderModule )
         */
-       public static function getModules() {
-               
-               self::initialize();
-               
-               return self::$modules;
+       public function getModules() {
+               return $this->modules;
        }
 
        /**
@@ -227,31 +221,8 @@ class ResourceLoader {
         * @param $name String: module name
         * @return mixed ResourceLoaderModule or null if not registered
         */
-       public static function getModule( $name ) {
-               
-               self::initialize();
-               
-               return isset( self::$modules[$name] ) ? self::$modules[$name] : null;
-       }
-
-       /**
-        * Get the highest modification time of all modules, based on a given 
-        * combination of language code, skin name and debug mode flag.
-        *
-        * @param $context ResourceLoaderContext object
-        * @return Integer: UNIX timestamp
-        */
-       public static function getHighestModifiedTime( ResourceLoaderContext $context ) {
-               
-               self::initialize();
-               
-               $time = 1; // wfTimestamp() treats 0 as 'now', so that's not a suitable choice
-
-               foreach ( self::$modules as $module ) {
-                       $time = max( $time, $module->getModifiedTime( $context ) );
-               }
-
-               return $time;
+       public function getModule( $name ) {
+               return isset( $this->modules[$name] ) ? $this->modules[$name] : null;
        }
 
        /**
@@ -259,19 +230,18 @@ class ResourceLoader {
         *
         * @param $context ResourceLoaderContext object
         */
-       public static function respond( ResourceLoaderContext $context ) {
+       public function respond( ResourceLoaderContext $context ) {
                global $wgResourceLoaderMaxage;
 
                wfProfileIn( __METHOD__ );
-               self::initialize();
                
                // Split requested modules into two groups, modules and missing
                $modules = array();
                $missing = array();
                
                foreach ( $context->getModules() as $name ) {
-                       if ( isset( self::$modules[$name] ) ) {
-                               $modules[$name] = self::$modules[$name];
+                       if ( isset( $this->modules[$name] ) ) {
+                               $modules[$name] = $this->modules[$name];
                        } else {
                                $missing[] = $name;
                        }
@@ -291,7 +261,7 @@ class ResourceLoader {
                }
 
                // Preload information needed to the mtime calculation below
-               self::preloadModuleInfo( array_keys( $modules ), $context );
+               $this->preloadModuleInfo( array_keys( $modules ), $context );
 
                // To send Last-Modified and support If-Modified-Since, we need to detect 
                // the last modified time
@@ -326,10 +296,10 @@ class ResourceLoader {
                wfProfileOut( __METHOD__ );
        }
 
-       public static function makeModuleResponse( ResourceLoaderContext $context, array $modules, $missing = null ) {
+       public function makeModuleResponse( ResourceLoaderContext $context, array $modules, $missing = null ) {
                // Pre-fetch blobs
                $blobs = $context->shouldIncludeMessages() ?
-                       MessageBlobStore::get( array_keys( $modules ), $context->getLanguage() ) : array();
+                       MessageBlobStore::get( $modules, $context->getLanguage() ) : array();
 
                // Generate output
                $out = '';
@@ -349,9 +319,9 @@ class ResourceLoader {
                                ( count( $styles = $module->getStyles( $context ) ) )
                        ) {
                                // Flip CSS on a per-module basis
-                               if ( self::$modules[$name]->getFlip( $context ) ) {
+                               if ( $this->modules[$name]->getFlip( $context ) ) {
                                        foreach ( $styles as $media => $style ) {
-                                               $styles[$media] = self::filter( 'flip-css', $style );
+                                               $styles[$media] = $this->filter( 'flip-css', $style );
                                        }
                                }
                        }
@@ -374,7 +344,7 @@ class ResourceLoader {
                                        // Minify CSS before embedding in mediaWiki.loader.implement call (unless in debug mode)
                                        if ( !$context->getDebug() ) {
                                                foreach ( $styles as $media => $style ) {
-                                                       $styles[$media] = self::filter( 'minify-css', $style );
+                                                       $styles[$media] = $this->filter( 'minify-css', $style );
                                                }
                                        }
                                        $out .= self::makeLoaderImplementScript( $name, $scripts, $styles, $messages );
@@ -400,14 +370,14 @@ class ResourceLoader {
                        return $out;
                } else {
                        if ( $context->getOnly() === 'styles' ) {
-                               return self::filter( 'minify-css', $out );
+                               return $this->filter( 'minify-css', $out );
                        } else {
-                               return self::filter( 'minify-js', $out );
+                               return $this->filter( 'minify-js', $out );
                        }
                }
        }
        
-       // Client code generation methods
+       /* Static Methods */
        
        public static function makeLoaderImplementScript( $name, $scripts, $styles, $messages ) {
                if ( is_array( $scripts ) ) {
index c8b3baf..1dca623 100644 (file)
@@ -30,6 +30,7 @@ class ResourceLoaderContext {
 
        /* Protected Members */
 
+       protected $resourceLoader;
        protected $request;
        protected $modules;
        protected $language;
@@ -43,9 +44,10 @@ class ResourceLoaderContext {
 
        /* Methods */
 
-       public function __construct( WebRequest $request ) {
+       public function __construct( ResourceLoader $resourceLoader, WebRequest $request ) {
                global $wgLang, $wgDefaultSkin, $wgResourceLoaderDebug;
 
+               $this->resourceLoader = $resourceLoader;
                $this->request = $request;
                // Interperet request
                $this->modules = explode( '|', $request->getVal( 'modules' ) );
@@ -71,6 +73,10 @@ class ResourceLoaderContext {
                }
        }
 
+       public function getResourceLoader() {
+               return $this->resourceLoader;
+       }
+       
        public function getRequest() {
                return $this->request;
        }
index 751cb1b..8e04643 100644 (file)
@@ -1054,7 +1054,7 @@ class ResourceLoaderStartUpModule extends ResourceLoaderModule {
                
                $out = '';
                $registrations = array();
-               foreach ( ResourceLoader::getModules() as $name => $module ) {
+               foreach ( $context->getResourceLoader()->getModules() as $name => $module ) {
                        // Support module loader scripts
                        if ( ( $loader = $module->getLoaderScript() ) !== false ) {
                                $deps = FormatJson::encode( $module->getDependencies() );
@@ -1104,8 +1104,8 @@ class ResourceLoaderStartUpModule extends ResourceLoaderModule {
                                'skin' => $context->getSkin(),
                                'debug' => $context->getDebug() ? 'true' : 'false',
                                'version' => wfTimestamp( TS_ISO_8601, round( max(
-                                       ResourceLoader::getModule( 'jquery' )->getModifiedTime( $context ),
-                                       ResourceLoader::getModule( 'mediawiki' )->getModifiedTime( $context )
+                                       $context->getResourceLoader()->getModule( 'jquery' )->getModifiedTime( $context ),
+                                       $context->getResourceLoader()->getModule( 'mediawiki' )->getModifiedTime( $context )
                                ), -2 ) )
                        );
                        // Ensure uniform query order
@@ -1132,10 +1132,14 @@ class ResourceLoaderStartUpModule extends ResourceLoaderModule {
                        return $this->modifiedTime[$hash];
                }
                $this->modifiedTime[$hash] = filemtime( "$IP/resources/startup.js" );
-               
+
                // ATTENTION!: Because of the line above, this is not going to cause infinite recursion - think carefully
                // before making changes to this code!
-               return $this->modifiedTime[$hash] = ResourceLoader::getHighestModifiedTime( $context );
+               $time = 1; // wfTimestamp() treats 0 as 'now', so that's not a suitable choice
+               foreach ( $context->getResourceLoader()->getModules() as $module ) {
+                       $time = max( $time, $module->getModifiedTime( $context ) );
+               }
+               return $this->modifiedTime[$hash] = $time;
        }
 
        public function getFlip( $context ) {
index 85c4f67..9f594e5 100644 (file)
--- a/load.php
+++ b/load.php
@@ -45,7 +45,8 @@ if ( $wgRequest->isPathInfoBad() ) {
 }
 
 // Respond to resource loading request
-ResourceLoader::respond( new ResourceLoaderContext( $wgRequest ) );
+$resourceLoader = new ResourceLoader();
+$resourceLoader->respond( new ResourceLoaderContext( $resourceLoader, $wgRequest ) );
 
 wfProfileOut( 'load.php' );
 wfLogProfilingData();
index 73c923f..98f5f0a 100644 (file)
@@ -1,6 +1,7 @@
 <?php
 
 class ResourceLoaderTest extends PHPUnit_Framework_TestCase {
+
        /* Provider Methods */
 
        public function provide() {