fabi1cazenave / webL10n

Client-side internationalization / localization library
http://fabi1cazenave.github.com/webL10n/
279 stars 71 forks source link

Always respect gAsyncResourceLoading flag #48 #52

Closed Rob--W closed 9 years ago

Rob--W commented 9 years ago

If gAsyncResourceLoading is true, all requests must be asynchronous, including requests generated by @import.

The patch might be easier to review if you only look at the non-space changes. Here is the diff excluding whitespace changes:

diff --git a/l10n.js b/l10n.js
index e97c376..1e35313 100644
--- a/l10n.js
+++ b/l10n.js
@@ -115,14 +115,14 @@ document.webL10n = (function(window, document, undefined) {
     document.dispatchEvent(evtObject);
   }

-  function xhrLoadText(url, onSuccess, onFailure, asynchronous) {
+  function xhrLoadText(url, onSuccess, onFailure) {
     onSuccess = onSuccess || function _onSuccess(data) {};
     onFailure = onFailure || function _onFailure() {
       consoleWarn(url + ' not found.');
     };

     var xhr = new XMLHttpRequest();
-    xhr.open('GET', url, asynchronous);
+    xhr.open('GET', url, gAsyncResourceLoading);
     if (xhr.overrideMimeType) {
       xhr.overrideMimeType('text/plain; charset=utf-8');
     }
@@ -191,7 +191,9 @@ document.webL10n = (function(window, document, undefined) {
     }

     // parse *.properties text data into an l10n dictionary
-    function parseProperties(text) {
+    // If gAsyncResourceLoading is false, then the callback will be called
+    // synchronously. Otherwise it is called asynchronously.
+    function parseProperties(text, parsedPropertiesCallback) {
       var dictionary = [];

       // token expressions
@@ -202,15 +204,22 @@ document.webL10n = (function(window, document, undefined) {
       var reSplit = /^([^=\s]*)\s*=\s*(.+)$/; // TODO: escape EOLs with '\'

       // parse the *.properties file into an associative array
-      function parseRawLines(rawText, extendedSyntax) {
+      function parseRawLines(rawText, extendedSyntax, parsedRawLinesCallback) {
         var entries = rawText.replace(reBlank, '').split(/[\r\n]+/);
         var currentLang = '*';
         var genericLang = lang.split('-', 1)[0];
         var skipLang = false;
         var match = '';

-        for (var i = 0; i < entries.length; i++) {
-          var line = entries[i];
+        function nextEntry() {
+          // Use infinite loop instead of recursion to avoid reaching the
+          // maximum recursion limit for content with many lines.
+          while (true) {
+            if (!entries.length) {
+              parsedRawLinesCallback();
+              return;
+            }
+            var line = entries.shift();

             // comment or blank line?
             if (reComment.test(line))
@@ -232,7 +241,8 @@ document.webL10n = (function(window, document, undefined) {
               }
               if (reImport.test(line)) { // @import rule?
                 match = reImport.exec(line);
-              loadImport(baseURL + match[1]); // load the resource synchronously
+                loadImport(baseURL + match[1], nextEntry);
+                return;
               }
             }

@@ -243,17 +253,20 @@ document.webL10n = (function(window, document, undefined) {
             }
           }
         }
+        nextEntry();
+      }

       // import another *.properties file
-      function loadImport(url) {
+      function loadImport(url, callback) {
         xhrLoadText(url, function(content) {
-          parseRawLines(content, false); // don't allow recursive imports
-        }, null, false); // load synchronously
+          parseRawLines(content, false, callback); // don't allow recursive imports
+        }, null);
       }

       // fill the dictionary
-      parseRawLines(text, true);
-      return dictionary;
+      parseRawLines(text, true, function() {
+        parsedPropertiesCallback(dictionary);
+      });
     }

     // load and parse l10n data (warning: global variables are used here)
@@ -261,7 +274,7 @@ document.webL10n = (function(window, document, undefined) {
       gTextData += response; // mostly for debug

       // parse *.properties text data into an l10n dictionary
-      var data = parseProperties(response);
+      parseProperties(response, function(data) {

         // find attribute descriptions, if any
         for (var key in data) {
@@ -283,7 +296,8 @@ document.webL10n = (function(window, document, undefined) {
         if (successCallback) {
           successCallback();
         }
-    }, failureCallback, gAsyncResourceLoading);
+      });
+    }, failureCallback);
   }

   // load and parse all resources for the specified locale
@@ -1033,13 +1047,13 @@ document.webL10n = (function(window, document, undefined) {

     // XMLHttpRequest for IE6
     if (!window.XMLHttpRequest) {
-      xhrLoadText = function(url, onSuccess, onFailure, asynchronous) {
+      xhrLoadText = function(url, onSuccess, onFailure) {
         onSuccess = onSuccess || function _onSuccess(data) {};
         onFailure = onFailure || function _onFailure() {
           consoleWarn(url + ' not found.');
         };
         var xhr = new ActiveXObject('Microsoft.XMLHTTP');
-        xhr.open('GET', url, asynchronous);
+        xhr.open('GET', url, gAsyncResourceLoading);
         xhr.onreadystatechange = function() {
           if (xhr.readyState == 4) {
             if (xhr.status == 200) {
fabi1cazenave commented 9 years ago

Nice stuff. ♡