Bug 1352324 - (Part 4) Fix eslint errors of PhoneNumber utility. r=MattN draft
authorLuke Chang <lchang@mozilla.com>
Wed, 28 Jun 2017 16:01:25 -0700
changeset 609616 d642a87ac21cc063ce7f609159300f8ec9f3c2c2
parent 609612 50be9a0904429b2e11a107cc967061f0108d5107
child 609617 3b70c07592943df74ed58aa85e51d573ebb7d99b
push id68602
push userbmo:lchang@mozilla.com
push dateMon, 17 Jul 2017 03:27:15 +0000
reviewersMattN
bugs1352324
milestone56.0a1
Bug 1352324 - (Part 4) Fix eslint errors of PhoneNumber utility. r=MattN MozReview-Commit-ID: 6UwifrRz3xA
.eslintignore
browser/extensions/formautofill/phonenumberutils/PhoneNumber.jsm
browser/extensions/formautofill/phonenumberutils/PhoneNumberNormalizer.jsm
--- a/.eslintignore
+++ b/.eslintignore
@@ -73,16 +73,18 @@ browser/extensions/pocket/content/panels
 browser/extensions/pocket/content/panels/js/vendor/**
 # generated or library files in activity-stream
 browser/extensions/activity-stream/data/content/activity-stream.bundle.js
 browser/extensions/activity-stream/vendor/**
 # The only file in browser/locales/ is pre-processed.
 browser/locales/**
 # imported from chromium
 browser/extensions/mortar/**
+# Generated data files
+browser/extensions/formautofill/phonenumberutils/PhoneNumberMetaData.jsm
 
 # devtools/ exclusions
 devtools/client/canvasdebugger/**
 devtools/client/commandline/**
 devtools/client/debugger/**
 devtools/client/framework/**
 !devtools/client/framework/devtools.js
 !devtools/client/framework/devtools-browser.js
--- a/browser/extensions/formautofill/phonenumberutils/PhoneNumber.jsm
+++ b/browser/extensions/formautofill/phonenumberutils/PhoneNumber.jsm
@@ -6,191 +6,206 @@
 // be further maintained by our own in Form Autofill codebase.
 
 "use strict";
 
 this.EXPORTED_SYMBOLS = ["PhoneNumber"];
 
 const Cu = Components.utils;
 
-Cu.import('resource://gre/modules/XPCOMUtils.jsm');
+Cu.import("resource://gre/modules/XPCOMUtils.jsm");
 XPCOMUtils.defineLazyModuleGetter(this, "PHONE_NUMBER_META_DATA",
                                   "resource://formautofill/phonenumberutils/PhoneNumberMetaData.jsm");
 XPCOMUtils.defineLazyModuleGetter(this, "PhoneNumberNormalizer",
                                   "resource://formautofill/phonenumberutils/PhoneNumberNormalizer.jsm");
-this.PhoneNumber = (function (dataBase) {
-  // Use strict in our context only - users might not want it
-  'use strict';
-
+this.PhoneNumber = (function(dataBase) {
   const MAX_PHONE_NUMBER_LENGTH = 50;
   const NON_ALPHA_CHARS = /[^a-zA-Z]/g;
   const NON_DIALABLE_CHARS = /[^,#+\*\d]/g;
   const NON_DIALABLE_CHARS_ONCE = new RegExp(NON_DIALABLE_CHARS.source);
   const BACKSLASH = /\\/g;
   const SPLIT_FIRST_GROUP = /^(\d+)(.*)$/;
   const LEADING_PLUS_CHARS_PATTERN = /^[+\uFF0B]+/g;
 
   // Format of the string encoded meta data. If the name contains "^" or "$"
   // we will generate a regular expression from the value, with those special
   // characters as prefix/suffix.
-  const META_DATA_ENCODING = ["region",
-                              "^(?:internationalPrefix)",
-                              "nationalPrefix",
-                              "^(?:nationalPrefixForParsing)",
-                              "nationalPrefixTransformRule",
-                              "nationalPrefixFormattingRule",
-                              "^possiblePattern$",
-                              "^nationalPattern$",
-                              "formats"];
+  const META_DATA_ENCODING = [
+    "region",
+    "^(?:internationalPrefix)",
+    "nationalPrefix",
+    "^(?:nationalPrefixForParsing)",
+    "nationalPrefixTransformRule",
+    "nationalPrefixFormattingRule",
+    "^possiblePattern$",
+    "^nationalPattern$",
+    "formats",
+  ];
 
-  const FORMAT_ENCODING = ["^pattern$",
-                           "nationalFormat",
-                           "^leadingDigits",
-                           "nationalPrefixFormattingRule",
-                           "internationalFormat"];
+  const FORMAT_ENCODING = [
+    "^pattern$",
+    "nationalFormat",
+    "^leadingDigits",
+    "nationalPrefixFormattingRule",
+    "internationalFormat",
+  ];
 
-  var regionCache = Object.create(null);
+  let regionCache = Object.create(null);
 
   // Parse an array of strings into a convenient object. We store meta
   // data as arrays since thats much more compact than JSON.
   function ParseArray(array, encoding, obj) {
-    for (var n = 0; n < encoding.length; ++n) {
-      var value = array[n];
-      if (!value)
+    for (let n = 0; n < encoding.length; ++n) {
+      let value = array[n];
+      if (!value) {
         continue;
-      var field = encoding[n];
-      var fieldAlpha = field.replace(NON_ALPHA_CHARS, "");
-      if (field != fieldAlpha)
+      }
+      let field = encoding[n];
+      let fieldAlpha = field.replace(NON_ALPHA_CHARS, "");
+      if (field != fieldAlpha) {
         value = new RegExp(field.replace(fieldAlpha, value));
+      }
       obj[fieldAlpha] = value;
     }
     return obj;
   }
 
   // Parse string encoded meta data into a convenient object
   // representation.
   function ParseMetaData(countryCode, md) {
-    var array = eval(md.replace(BACKSLASH, "\\\\"));
+    /* eslint-disable no-eval */
+    let array = eval(md.replace(BACKSLASH, "\\\\"));
     md = ParseArray(array,
                     META_DATA_ENCODING,
-                    { countryCode: countryCode });
+                    {countryCode});
     regionCache[md.region] = md;
     return md;
   }
 
   // Parse string encoded format data into a convenient object
   // representation.
   function ParseFormat(md) {
-    var formats = md.formats;
+    let formats = md.formats;
     if (!formats) {
-      return null;
+      return;
     }
     // Bail if we already parsed the format definitions.
-    if (!(Array.isArray(formats[0])))
+    if (!(Array.isArray(formats[0]))) {
       return;
-    for (var n = 0; n < formats.length; ++n) {
+    }
+    for (let n = 0; n < formats.length; ++n) {
       formats[n] = ParseArray(formats[n],
                               FORMAT_ENCODING,
                               {});
     }
   }
 
   // Search for the meta data associated with a region identifier ("US") in
   // our database, which is indexed by country code ("1"). Since we have
   // to walk the entire database for this, we cache the result of the lookup
   // for future reference.
   function FindMetaDataForRegion(region) {
     // Check in the region cache first. This will find all entries we have
     // already resolved (parsed from a string encoding).
-    var md = regionCache[region];
-    if (md)
+    let md = regionCache[region];
+    if (md) {
       return md;
-    for (var countryCode in dataBase) {
-      var entry = dataBase[countryCode];
+    }
+    for (let countryCode in dataBase) {
+      let entry = dataBase[countryCode];
       // Each entry is a string encoded object of the form '["US..', or
       // an array of strings. We don't want to parse the string here
       // to save memory, so we just substring the region identifier
       // and compare it. For arrays, we compare against all region
       // identifiers with that country code. We skip entries that are
       // of type object, because they were already resolved (parsed into
       // an object), and their country code should have been in the cache.
       if (Array.isArray(entry)) {
-        for (var n = 0; n < entry.length; n++) {
-          if (typeof entry[n] == "string" && entry[n].substr(2,2) == region) {
+        for (let n = 0; n < entry.length; n++) {
+          if (typeof entry[n] == "string" && entry[n].substr(2, 2) == region) {
             if (n > 0) {
               // Only the first entry has the formats field set.
               // Parse the main country if we haven't already and use
               // the formats field from the main country.
-              if (typeof entry[0] == "string")
+              if (typeof entry[0] == "string") {
                 entry[0] = ParseMetaData(countryCode, entry[0]);
+              }
               let formats = entry[0].formats;
               let current = ParseMetaData(countryCode, entry[n]);
               current.formats = formats;
-              return entry[n] = current;
+              entry[n] = current;
+              return entry[n];
             }
 
             entry[n] = ParseMetaData(countryCode, entry[n]);
             return entry[n];
           }
         }
         continue;
       }
-      if (typeof entry == "string" && entry.substr(2,2) == region)
-        return dataBase[countryCode] = ParseMetaData(countryCode, entry);
+      if (typeof entry == "string" && entry.substr(2, 2) == region) {
+        dataBase[countryCode] = ParseMetaData(countryCode, entry);
+        return dataBase[countryCode];
+      }
     }
   }
 
   // Format a national number for a given region. The boolean flag "intl"
   // indicates whether we want the national or international format.
   function FormatNumber(regionMetaData, number, intl) {
     // We lazily parse the format description in the meta data for the region,
     // so make sure to parse it now if we haven't already done so.
     ParseFormat(regionMetaData);
-    var formats = regionMetaData.formats;
+    let formats = regionMetaData.formats;
     if (!formats) {
       return null;
     }
-    for (var n = 0; n < formats.length; ++n) {
-      var format = formats[n];
+    for (let n = 0; n < formats.length; ++n) {
+      let format = formats[n];
       // The leading digits field is optional. If we don't have it, just
       // use the matching pattern to qualify numbers.
-      if (format.leadingDigits && !format.leadingDigits.test(number))
+      if (format.leadingDigits && !format.leadingDigits.test(number)) {
         continue;
-      if (!format.pattern.test(number))
+      }
+      if (!format.pattern.test(number)) {
         continue;
+      }
       if (intl) {
         // If there is no international format, just fall back to the national
         // format.
-        var internationalFormat = format.internationalFormat;
-        if (!internationalFormat)
+        let internationalFormat = format.internationalFormat;
+        if (!internationalFormat) {
           internationalFormat = format.nationalFormat;
+        }
         // Some regions have numbers that can't be dialed from outside the
         // country, indicated by "NA" for the international format of that
         // number format pattern.
-        if (internationalFormat == "NA")
+        if (internationalFormat == "NA") {
           return null;
+        }
         // Prepend "+" and the country code.
         number = "+" + regionMetaData.countryCode + " " +
                  number.replace(format.pattern, internationalFormat);
       } else {
         number = number.replace(format.pattern, format.nationalFormat);
         // The region has a national prefix formatting rule, and it can be overwritten
         // by each actual number format rule.
-        var nationalPrefixFormattingRule = regionMetaData.nationalPrefixFormattingRule;
-        if (format.nationalPrefixFormattingRule)
+        let nationalPrefixFormattingRule = regionMetaData.nationalPrefixFormattingRule;
+        if (format.nationalPrefixFormattingRule) {
           nationalPrefixFormattingRule = format.nationalPrefixFormattingRule;
+        }
         if (nationalPrefixFormattingRule) {
           // The prefix formatting rule contains two magic markers, "$NP" and "$FG".
           // "$NP" will be replaced by the national prefix, and "$FG" with the
           // first group of numbers.
-          var match = number.match(SPLIT_FIRST_GROUP);
+          let match = number.match(SPLIT_FIRST_GROUP);
           if (match) {
-            var firstGroup = match[1];
-            var rest = match[2];
-            var prefix = nationalPrefixFormattingRule;
+            let firstGroup = match[1];
+            let rest = match[2];
+            let prefix = nationalPrefixFormattingRule;
             prefix = prefix.replace("$NP", regionMetaData.nationalPrefix);
             prefix = prefix.replace("$FG", firstGroup);
             number = prefix + rest;
           }
         }
       }
       return (number == "NA") ? null : number;
     }
@@ -205,221 +220,236 @@ this.PhoneNumber = (function (dataBase) 
 
   // NationalNumber represents the result of parsing a phone number. We have
   // three getters on the prototype that format the number in national and
   // international format. Once called, the getters put a direct property
   // onto the object, caching the result.
   NationalNumber.prototype = {
     // +1 949-726-2896
     get internationalFormat() {
-      var value = FormatNumber(this.regionMetaData, this.number, true);
-      Object.defineProperty(this, "internationalFormat", { value: value, enumerable: true });
+      let value = FormatNumber(this.regionMetaData, this.number, true);
+      Object.defineProperty(this, "internationalFormat", {value, enumerable: true});
       return value;
     },
     // (949) 726-2896
     get nationalFormat() {
-      var value = FormatNumber(this.regionMetaData, this.number, false);
-      Object.defineProperty(this, "nationalFormat", { value: value, enumerable: true });
+      let value = FormatNumber(this.regionMetaData, this.number, false);
+      Object.defineProperty(this, "nationalFormat", {value, enumerable: true});
       return value;
     },
     // +19497262896
     get internationalNumber() {
-      var value = this.internationalFormat ? this.internationalFormat.replace(NON_DIALABLE_CHARS, "")
+      let value = this.internationalFormat ? this.internationalFormat.replace(NON_DIALABLE_CHARS, "")
                                            : null;
-      Object.defineProperty(this, "internationalNumber", { value: value, enumerable: true });
+      Object.defineProperty(this, "internationalNumber", {value, enumerable: true});
       return value;
     },
     // 9497262896
     get nationalNumber() {
-      var value = this.nationalFormat ? this.nationalFormat.replace(NON_DIALABLE_CHARS, "")
+      let value = this.nationalFormat ? this.nationalFormat.replace(NON_DIALABLE_CHARS, "")
                                       : null;
-      Object.defineProperty(this, "nationalNumber", { value: value, enumerable: true });
+      Object.defineProperty(this, "nationalNumber", {value, enumerable: true});
       return value;
     },
     // country name 'US'
     get countryName() {
-      var value = this.region ? this.region : null;
-      Object.defineProperty(this, "countryName", { value: value, enumerable: true });
+      let value = this.region ? this.region : null;
+      Object.defineProperty(this, "countryName", {value, enumerable: true});
       return value;
     },
     // country code '+1'
     get countryCode() {
-      var value = this.regionMetaData.countryCode ? "+" + this.regionMetaData.countryCode : null;
-      Object.defineProperty(this, "countryCode", { value: value, enumerable: true });
+      let value = this.regionMetaData.countryCode ? "+" + this.regionMetaData.countryCode : null;
+      Object.defineProperty(this, "countryCode", {value, enumerable: true});
       return value;
-    }
+    },
   };
 
   // Check whether the number is valid for the given region.
   function IsValidNumber(number, md) {
     return md.possiblePattern.test(number);
   }
 
   // Check whether the number is a valid national number for the given region.
+  /* eslint-disable no-unused-vars */
   function IsNationalNumber(number, md) {
     return IsValidNumber(number, md) && md.nationalPattern.test(number);
   }
 
   // Determine the country code a number starts with, or return null if
   // its not a valid country code.
   function ParseCountryCode(number) {
-    for (var n = 1; n <= 3; ++n) {
-      var cc = number.substr(0,n);
-      if (dataBase[cc])
+    for (let n = 1; n <= 3; ++n) {
+      let cc = number.substr(0, n);
+      if (dataBase[cc]) {
         return cc;
+      }
     }
     return null;
   }
 
-  // Parse an international number that starts with the country code. Return
-  // null if the number is not a valid international number.
-  function ParseInternationalNumber(number) {
-    // Parse and strip the country code.
-    var countryCode = ParseCountryCode(number);
-    if (!countryCode)
-      return null;
-    number = number.substr(countryCode.length);
-
-    return ParseNumberByCountryCode(number, countryCode);
-  }
-
-  function ParseNumberByCountryCode(number, countryCode) {
-    var ret;
-
-    // Lookup the meta data for the region (or regions) and if the rest of
-    // the number parses for that region, return the parsed number.
-    var entry = dataBase[countryCode];
-    if (Array.isArray(entry)) {
-      for (var n = 0; n < entry.length; ++n) {
-        if (typeof entry[n] == "string")
-          entry[n] = ParseMetaData(countryCode, entry[n]);
-        if (n > 0)
-          entry[n].formats = entry[0].formats;
-        ret = ParseNationalNumberAndCheckNationalPrefix(number, entry[n]);
-        if (ret)
-          return ret;
-      }
-      return null;
-    }
-    if (typeof entry == "string")
-      entry = dataBase[countryCode] = ParseMetaData(countryCode, entry);
-    return ParseNationalNumberAndCheckNationalPrefix(number, entry);
-  }
-
-  function ParseNationalNumberAndCheckNationalPrefix(number, md) {
-    var ret;
-
-    // This is not an international number. See if its a national one for
-    // the current region. National numbers can start with the national
-    // prefix, or without.
-    if (md.nationalPrefixForParsing) {
-      // Some regions have specific national prefix parse rules. Apply those.
-      var withoutPrefix = number.replace(md.nationalPrefixForParsing,
-                                         md.nationalPrefixTransformRule || '');
-      ret = ParseNationalNumber(withoutPrefix, md)
-      if (ret)
-        return ret;
-    } else {
-      // If there is no specific national prefix rule, just strip off the
-      // national prefix from the beginning of the number (if there is one).
-      var nationalPrefix = md.nationalPrefix;
-      if (nationalPrefix && number.indexOf(nationalPrefix) == 0 &&
-          (ret = ParseNationalNumber(number.substr(nationalPrefix.length), md))) {
-        return ret;
-      }
-    }
-    ret = ParseNationalNumber(number, md)
-    if (ret)
-      return ret;
-  }
-
   // Parse a national number for a specific region. Return null if the
   // number is not a valid national number (it might still be a possible
   // number for parts of that region).
   function ParseNationalNumber(number, md) {
     if (!md.possiblePattern.test(number) ||
         !md.nationalPattern.test(number)) {
       return null;
     }
     // Success.
     return new NationalNumber(md, number);
   }
 
+  function ParseNationalNumberAndCheckNationalPrefix(number, md) {
+    let ret;
+
+    // This is not an international number. See if its a national one for
+    // the current region. National numbers can start with the national
+    // prefix, or without.
+    if (md.nationalPrefixForParsing) {
+      // Some regions have specific national prefix parse rules. Apply those.
+      let withoutPrefix = number.replace(md.nationalPrefixForParsing,
+                                         md.nationalPrefixTransformRule || "");
+      ret = ParseNationalNumber(withoutPrefix, md);
+      if (ret) {
+        return ret;
+      }
+    } else {
+      // If there is no specific national prefix rule, just strip off the
+      // national prefix from the beginning of the number (if there is one).
+      let nationalPrefix = md.nationalPrefix;
+      if (nationalPrefix && number.indexOf(nationalPrefix) == 0 &&
+          (ret = ParseNationalNumber(number.substr(nationalPrefix.length), md))) {
+        return ret;
+      }
+    }
+    ret = ParseNationalNumber(number, md);
+    if (ret) {
+      return ret;
+    }
+  }
+
+  function ParseNumberByCountryCode(number, countryCode) {
+    let ret;
+
+    // Lookup the meta data for the region (or regions) and if the rest of
+    // the number parses for that region, return the parsed number.
+    let entry = dataBase[countryCode];
+    if (Array.isArray(entry)) {
+      for (let n = 0; n < entry.length; ++n) {
+        if (typeof entry[n] == "string") {
+          entry[n] = ParseMetaData(countryCode, entry[n]);
+        }
+        if (n > 0) {
+          entry[n].formats = entry[0].formats;
+        }
+        ret = ParseNationalNumberAndCheckNationalPrefix(number, entry[n]);
+        if (ret) {
+          return ret;
+        }
+      }
+      return null;
+    }
+    if (typeof entry == "string") {
+      entry = dataBase[countryCode] = ParseMetaData(countryCode, entry);
+    }
+    return ParseNationalNumberAndCheckNationalPrefix(number, entry);
+  }
+
+  // Parse an international number that starts with the country code. Return
+  // null if the number is not a valid international number.
+  function ParseInternationalNumber(number) {
+    // Parse and strip the country code.
+    let countryCode = ParseCountryCode(number);
+    if (!countryCode) {
+      return null;
+    }
+    number = number.substr(countryCode.length);
+
+    return ParseNumberByCountryCode(number, countryCode);
+  }
+
   // Parse a number and transform it into the national format, removing any
   // international dial prefixes and country codes.
   function ParseNumber(number, defaultRegion) {
-    var ret;
+    let ret;
 
     // Remove formating characters and whitespace.
     number = PhoneNumberNormalizer.Normalize(number);
 
     // If there is no defaultRegion or the defaultRegion is the global region,
     // we can't parse international access codes.
-    if ((!defaultRegion || defaultRegion === '001') && number[0] !== '+')
+    if ((!defaultRegion || defaultRegion === "001") && number[0] !== "+") {
       return null;
+    }
 
     // Detect and strip leading '+'.
-    if (number[0] === '+')
+    if (number[0] === "+") {
       return ParseInternationalNumber(number.replace(LEADING_PLUS_CHARS_PATTERN, ""));
+    }
 
     // If "defaultRegion" is a country code, use it to parse the number directly.
-    var matches = String(defaultRegion).match(/^\+?(\d+)/);
+    let matches = String(defaultRegion).match(/^\+?(\d+)/);
     if (matches) {
-      var countryCode = ParseCountryCode(matches[1]);
+      let countryCode = ParseCountryCode(matches[1]);
       if (!countryCode) {
         return null;
       }
       return ParseNumberByCountryCode(number, countryCode);
     }
 
     // Lookup the meta data for the given region.
-    var md = FindMetaDataForRegion(defaultRegion.toUpperCase());
+    let md = FindMetaDataForRegion(defaultRegion.toUpperCase());
 
     if (!md) {
       dump("Couldn't find Meta Data for region: " + defaultRegion + "\n");
       return null;
     }
 
     // See if the number starts with an international prefix, and if the
     // number resulting from stripping the code is valid, then remove the
     // prefix and flag the number as international.
     if (md.internationalPrefix.test(number)) {
-      var possibleNumber = number.replace(md.internationalPrefix, "");
-      ret = ParseInternationalNumber(possibleNumber)
-      if (ret)
+      let possibleNumber = number.replace(md.internationalPrefix, "");
+      ret = ParseInternationalNumber(possibleNumber);
+      if (ret) {
         return ret;
+      }
     }
 
     ret = ParseNationalNumberAndCheckNationalPrefix(number, md);
-    if (ret)
+    if (ret) {
       return ret;
+    }
 
     // Now lets see if maybe its an international number after all, but
     // without '+' or the international prefix.
-    ret = ParseInternationalNumber(number)
-    if (ret)
+    ret = ParseInternationalNumber(number);
+    if (ret) {
       return ret;
+    }
 
     // If the number matches the possible numbers of the current region,
     // return it as a possible number.
-    if (md.possiblePattern.test(number))
+    if (md.possiblePattern.test(number)) {
       return new NationalNumber(md, number);
+    }
 
     // We couldn't parse the number at all.
     return null;
   }
 
   function IsPlainPhoneNumber(number) {
-    if (typeof number !== 'string') {
+    if (typeof number !== "string") {
       return false;
     }
 
-    var length = number.length;
-    var isTooLong = (length > MAX_PHONE_NUMBER_LENGTH);
-    var isEmpty = (length === 0);
+    let length = number.length;
+    let isTooLong = (length > MAX_PHONE_NUMBER_LENGTH);
+    let isEmpty = (length === 0);
     return !(isTooLong || isEmpty || NON_DIALABLE_CHARS_ONCE.test(number));
   }
 
   return {
     IsPlain: IsPlainPhoneNumber,
     Parse: ParseNumber,
   };
 })(PHONE_NUMBER_META_DATA);
--- a/browser/extensions/formautofill/phonenumberutils/PhoneNumberNormalizer.jsm
+++ b/browser/extensions/formautofill/phonenumberutils/PhoneNumberNormalizer.jsm
@@ -11,46 +11,46 @@ this.EXPORTED_SYMBOLS = ["PhoneNumberNor
 
 this.PhoneNumberNormalizer = (function() {
   const UNICODE_DIGITS = /[\uFF10-\uFF19\u0660-\u0669\u06F0-\u06F9]/g;
   const VALID_ALPHA_PATTERN = /[a-zA-Z]/g;
   const LEADING_PLUS_CHARS_PATTERN = /^[+\uFF0B]+/g;
   const NON_DIALABLE_CHARS = /[^,#+\*\d]/g;
 
   // Map letters to numbers according to the ITU E.161 standard
-  var E161 = {
-    'a': 2, 'b': 2, 'c': 2,
-    'd': 3, 'e': 3, 'f': 3,
-    'g': 4, 'h': 4, 'i': 4,
-    'j': 5, 'k': 5, 'l': 5,
-    'm': 6, 'n': 6, 'o': 6,
-    'p': 7, 'q': 7, 'r': 7, 's': 7,
-    't': 8, 'u': 8, 'v': 8,
-    'w': 9, 'x': 9, 'y': 9, 'z': 9
+  let E161 = {
+    "a": 2, "b": 2, "c": 2,
+    "d": 3, "e": 3, "f": 3,
+    "g": 4, "h": 4, "i": 4,
+    "j": 5, "k": 5, "l": 5,
+    "m": 6, "n": 6, "o": 6,
+    "p": 7, "q": 7, "r": 7, "s": 7,
+    "t": 8, "u": 8, "v": 8,
+    "w": 9, "x": 9, "y": 9, "z": 9,
   };
 
   // Normalize a number by converting unicode numbers and symbols to their
   // ASCII equivalents and removing all non-dialable characters.
   function NormalizeNumber(number, numbersOnly) {
-    if (typeof number !== 'string') {
-      return '';
+    if (typeof number !== "string") {
+      return "";
     }
 
     number = number.replace(UNICODE_DIGITS,
-                            function (ch) {
+                            function(ch) {
                               return String.fromCharCode(48 + (ch.charCodeAt(0) & 0xf));
                             });
     if (!numbersOnly) {
       number = number.replace(VALID_ALPHA_PATTERN,
-                              function (ch) {
+                              function(ch) {
                                 return String(E161[ch.toLowerCase()] || 0);
                               });
     }
     number = number.replace(LEADING_PLUS_CHARS_PATTERN, "+");
     number = number.replace(NON_DIALABLE_CHARS, "");
     return number;
-  };
+  }
 
 
   return {
-    Normalize: NormalizeNumber
+    Normalize: NormalizeNumber,
   };
-})();
\ No newline at end of file
+})();