Merge pull request #94 from googlei18n/opensource_update_15416

(AUTOMATIC) opensource update
diff --git a/android/src/androidTest/AndroidManifest.xml b/android/src/androidTest/AndroidManifest.xml
index d16ab0d..2d267f6 100644
--- a/android/src/androidTest/AndroidManifest.xml
+++ b/android/src/androidTest/AndroidManifest.xml
@@ -1,6 +1,6 @@
 <?xml version="1.0" encoding="utf-8"?>
 <manifest xmlns:android="http://schemas.android.com/apk/res/android"
-    package="com.android.i18n.addressinput"
+    package="com.android.i18n.addressinput.test"
     android:versionCode="1"
     android:versionName="1.0" >
 
@@ -8,11 +8,12 @@
         android:minSdkVersion="9"
         android:targetSdkVersion="22" />
 
-<!--
+    <!-- Gradle generates an <instrumentation> block during the build process,
+         but in order to work with other build systems, that don't do that,
+         there must be such a block declared here. -->
     <instrumentation
         android:name="android.test.InstrumentationTestRunner"
-        android:targetPackage="com.android.i18n.addressinput" />
--->
+        android:targetPackage="com.android.i18n.addressinput.test" />
 
     <uses-permission android:name="android.permission.INTERNET" />
 
@@ -20,7 +21,8 @@
         android:allowBackup="false"
         android:icon="@android:drawable/sym_def_app_icon" >
         <uses-library android:name="android.test.runner" />
-        <activity android:name=".testing.TestActivity" />
+        <activity
+            android:name="com.android.i18n.addressinput.testing.TestActivity" />
     </application>
 
 </manifest>
diff --git a/android/src/main/java/com/android/i18n/addressinput/AddressWidget.java b/android/src/main/java/com/android/i18n/addressinput/AddressWidget.java
index 4e6e983..349e536 100644
--- a/android/src/main/java/com/android/i18n/addressinput/AddressWidget.java
+++ b/android/src/main/java/com/android/i18n/addressinput/AddressWidget.java
@@ -233,9 +233,9 @@
 
   private AddressWidgetUiComponentProvider componentProvider;
 
-  /** TODO: Add region-dependent width types for address fields. */
   private WidthType getFieldWidthType(AddressUiComponent field) {
-    return field.getId().getDefaultWidthType();
+    // TODO(user): For drop-downs (spinners), derive the width-type from the list of values.
+    return field.getId().getWidthTypeForRegion(currentRegion);
   }
 
   private void createView(ViewGroup rootView, AddressUiComponent field, String defaultKey,
@@ -760,14 +760,13 @@
     return null;
   }
 
-  private String getErrorMessageForInvalidEntry(AddressData address, AddressField field,
+  public String getErrorMessageForInvalidEntry(AddressData address, AddressField field,
       AddressProblemType problem) {
     switch (problem) {
       case MISSING_REQUIRED_FIELD:
         return context.getString(R.string.i18n_missing_required_field);
       case UNKNOWN_VALUE:
-        String currentValue = address.getFieldValue(field);
-        return String.format(context.getString(R.string.unknown_entry), currentValue);
+        return context.getString(R.string.unknown_entry);
       case INVALID_FORMAT:
         // We only support this error type for the Postal Code field.
         if (zipLabel == ZipLabel.POSTAL) {
diff --git a/android/src/main/res/values/address_strings.xml b/android/src/main/res/values/address_strings.xml
index 7a6d2bd..78a9dc3 100644
--- a/android/src/main/res/values/address_strings.xml
+++ b/android/src/main/res/values/address_strings.xml
@@ -46,7 +46,7 @@
 
     <string name="i18n_address_line1_label" translation_description="Street-level part of an address, e.g. &quot;18th Street, Unit 3&quot;. [CHAR LIMIT=30]">Street address</string>
 
-    <string name="i18n_pin_code_label" translation_description="PIN (Postal Index Number) Code. Values are numeric. Used in India. [CHAR LIMIT=30]">PIN code</string>
+    <string name="i18n_pin_code_label" translation_description="PIN (Postal Index Number) Code. Values are numeric. Used in India. [CHAR LIMIT=30]">Pincode</string>
 
     <string name="i18n_postal_code_label" translation_description="Postal Code. Values are frequently alphanumeric. Used in countries such as Switzerland. [CHAR LIMIT=30]">Postal code</string>
 
@@ -82,21 +82,21 @@
 
     <string name="i18n_organization_label" translation_description="Label for the field of organization, firm, company, or institution in an address. Examples of values in this field: Google, Department of Transportation, University of Cambridge. [CHAR LIMIT=30]">Organization</string>
 
-    <string name="i18n_missing_required_field" translation_description="Error message shown with a UI field when it is a required field and the user has not filled it out. [CHAR LIMIT=30]">You can\u0027t leave this empty.</string>
+    <string name="i18n_missing_required_field" translation_description="Error message shown with a UI field when it is a required field and the user has not filled it out. [CHAR LIMIT=20]">Required field</string>
 
-    <string name="unknown_entry" translation_description="Occurs when the user fills out the wrong value for an address field. For example, this would be shown when putting 'Cupertino' in United States' State field. [CHAR LIMIT=60]">%1$s is not recognized as a known value for this field.</string>
+    <string name="unknown_entry" translation_description="Occurs when the user fills out the wrong value for an address field. For example, this would be shown when putting 'Cupertino' in United States' State field. [CHAR LIMIT=20]">Invalid entry</string>
 
-    <string name="unrecognized_format_pin_code" translation_description="Occurs when the user fills out a PIN code that does not conform to the country's PIN code format. For example, this would be shown when using '123' as an Indian PIN code, which is normally 6 digits long. [CHAR LIMIT=60]">This PIN code format is not recognized.</string>
+    <string name="unrecognized_format_pin_code" translation_description="Occurs when the user fills out a PIN code that does not conform to the country's PIN code format. For example, this would be shown when using '123' as an Indian PIN code, which is normally 6 digits long. [CHAR LIMIT=20]">Enter valid Pincode</string>
 
-    <string name="unrecognized_format_postal_code" translation_description="Occurs when the user fills out a postal code that does not conform to the country's postal code format. For example, this would be shown when using '80' as a Swiss postal code, which is normally 4 digits long. [CHAR LIMIT=60]">This postal code format is not recognized.</string>
+    <string name="unrecognized_format_postal_code" translation_description="Occurs when the user fills out a postal code that does not conform to the country's postal code format. For example, this would be shown when using '80' as a Swiss postal code, which is normally 4 digits long. [CHAR LIMIT=20]">Enter valid code</string>
 
-    <string name="unrecognized_format_zip_code" translation_description="Occurs when the user fills out a ZIP code that does not conform to the country's ZIP code format. For example, this would be shown when using '901' as a ZIP code for the United States. [CHAR LIMIT=60]">This ZIP code format is not recognized.</string>
+    <string name="unrecognized_format_zip_code" translation_description="Occurs when the user fills out a ZIP code that does not conform to the country's ZIP code format. For example, this would be shown when using '901' as a ZIP code for the United States. [CHAR LIMIT=20]">Enter valid ZIP</string>
 
-    <string name="mismatching_value_pin_code" translation_description="Occurs when the user fills out the wrong PIN code for a certain location. For example, this would be shown when using 456001 for New Delhi, India. [CHAR LIMIT=70]">This PIN code does not appear to match the rest of this address.</string>
+    <string name="mismatching_value_pin_code" translation_description="Occurs when the user fills out the wrong PIN code for a certain location. For example, this would be shown when using 456001 for New Delhi, India. [CHAR LIMIT=20]">Must match address</string>
 
-    <string name="mismatching_value_postal_code" translation_description="Occurs when the user fills out the wrong postal code for a certain location. For example, this would be shown when using Z3Z 2Y7 for Alberta, Canada. [CHAR LIMIT=70]">This postal code does not appear to match the rest of this address.</string>
+    <string name="mismatching_value_postal_code" translation_description="Occurs when the user fills out the wrong postal code for a certain location. For example, this would be shown when using Z3Z 2Y7 for Alberta, Canada. [CHAR LIMIT=20]">Must match address</string>
 
-    <string name="mismatching_value_zip_code" translation_description="Occurs when the user fills out the wrong ZIP code for a certain location. For example, this would be shown when using 10001 for Arizona state. [CHAR LIMIT=70]">This ZIP code does not appear to match the rest of this address.</string>
+    <string name="mismatching_value_zip_code" translation_description="Occurs when the user fills out the wrong ZIP code for a certain location. For example, this would be shown when using 10001 for Arizona state. [CHAR LIMIT=20]">Must match address</string>
 
     <string name="i18n_address_line1_accessibility_label" translation_description="Accessibility label for the text field of the first street address line. [CHAR LIMIT=50]">Street address: line 1</string>
 
diff --git a/common/src/main/java/com/google/i18n/addressinput/common/AddressDataKey.java b/common/src/main/java/com/google/i18n/addressinput/common/AddressDataKey.java
index a74a699..3b8fb49 100644
--- a/common/src/main/java/com/google/i18n/addressinput/common/AddressDataKey.java
+++ b/common/src/main/java/com/google/i18n/addressinput/common/AddressDataKey.java
@@ -92,6 +92,10 @@
    */
   SUB_NAMES,
   /**
+   * Encodes width overrides for specific fields.
+   */
+  WIDTH_OVERRIDES,
+  /**
    * Encodes the {@link #ZIP} value for the subtree beneath this region.
    */
   XZIP,
diff --git a/common/src/main/java/com/google/i18n/addressinput/common/AddressField.java b/common/src/main/java/com/google/i18n/addressinput/common/AddressField.java
index c133a87..08e570e 100644
--- a/common/src/main/java/com/google/i18n/addressinput/common/AddressField.java
+++ b/common/src/main/java/com/google/i18n/addressinput/common/AddressField.java
@@ -80,6 +80,19 @@
      * Identifies an input field as accepting short (often bounded) input, such as postal code.
      */
     SHORT;
+
+    static WidthType of(char c) {
+      switch (c) {
+        // In case we need a 'narrow'. Map it to 'S' for now to facilitate the rollout.
+        case 'N':
+        case 'S':
+          return SHORT;
+        case 'L':
+          return LONG;
+        default:
+          throw new IllegalArgumentException("invalid width character: " + c);
+      }
+    }
   }
 
   private static final Map<Character, AddressField> FIELD_MAPPING;
@@ -129,7 +142,18 @@
    * field, in the UI.
    */
   // TODO: We'd probably be better off just having a widthType field in the enum.
-  public WidthType getDefaultWidthType() {
+  private WidthType getDefaultWidthType() {
     return this.equals(POSTAL_CODE) || this.equals(SORTING_CODE) ? WidthType.SHORT : WidthType.LONG;
   }
+
+  /**
+   * Returns default width of this address field. Takes per-country heuristics into account for
+   * text input fields. This may be overridden for a specific country when we have data for the
+   * possible inputs in that field and use a drop-down, rather than a text field, in the UI.
+   */
+  public WidthType getWidthTypeForRegion(String regionCode) {
+    Util.checkNotNull(regionCode);
+    WidthType width = FormatInterpreter.getWidthOverride(this, regionCode);
+    return width != null ? width : getDefaultWidthType();
+  }
 }
diff --git a/common/src/main/java/com/google/i18n/addressinput/common/FormatInterpreter.java b/common/src/main/java/com/google/i18n/addressinput/common/FormatInterpreter.java
index 1c7673e..fea3035 100644
--- a/common/src/main/java/com/google/i18n/addressinput/common/FormatInterpreter.java
+++ b/common/src/main/java/com/google/i18n/addressinput/common/FormatInterpreter.java
@@ -16,6 +16,7 @@
 
 package com.google.i18n.addressinput.common;
 
+import com.google.i18n.addressinput.common.AddressField.WidthType;
 import com.google.i18n.addressinput.common.LookupKey.ScriptType;
 
 import org.json.JSONException;
@@ -26,6 +27,7 @@
 import java.util.Collections;
 import java.util.EnumSet;
 import java.util.List;
+import java.util.Map;
 import java.util.Set;
 
 /**
@@ -140,6 +142,56 @@
   }
 
   /**
+   * Returns the field width override for the specified country, or null if there's none. This is
+   * based upon the "width_overrides" field in RegionDataConstants for {@code regionCode}.
+   */
+  static WidthType getWidthOverride(AddressField field, String regionCode) {
+    return getWidthOverride(field, regionCode, RegionDataConstants.getCountryFormatMap());
+  }
+
+  /**
+   * Visible for Testing - same as {@link #getWidthOverride(AddressField, String)} but testable with
+   * fake data.
+   */
+  static WidthType getWidthOverride(
+      AddressField field, String regionCode, Map<String, String> regionDataMap) {
+    Util.checkNotNull(regionCode);
+    String overridesString =
+        getJsonValue(regionCode, AddressDataKey.WIDTH_OVERRIDES, regionDataMap);
+    if (overridesString == null || overridesString.isEmpty()) {
+      return null;
+    }
+
+    // The field width overrides string starts with a %, so we skip the first one.
+    // Example string: "%C:L%S:S" which is a repeated string of
+    // '<%> field_character <:> width_character'.
+    for (int pos = 0; pos != -1;) {
+      int keyStartIndex = pos + 1;
+      int valueStartIndex = overridesString.indexOf(':', keyStartIndex + 1) + 1;
+      if (valueStartIndex == 0 || valueStartIndex == overridesString.length()) {
+        // Malformed string -- % not followed by ':' or trailing ':'
+        return null;
+      }
+      // Prepare for next iteration.
+      pos = overridesString.indexOf('%', valueStartIndex + 1);
+      if (valueStartIndex != keyStartIndex + 2 ||
+          overridesString.charAt(keyStartIndex) != field.getChar()) {
+        // Key is not a high level field (unhandled by this code) or does not match.
+        // Also catches malformed string where key is of zero length (skip, not error).
+        continue;
+      }
+      int valueLength = (pos != -1 ? pos : overridesString.length()) - valueStartIndex;
+      if (valueLength != 1) {
+        // Malformed string -- value has length other than 1
+        return null;
+      }
+      return WidthType.of(overridesString.charAt(valueStartIndex));
+    }
+
+    return null;
+  }
+
+  /**
    * Gets formatted address. For example,
    *
    * <p> John Doe<br> Dnar Corp<br> 5th St<br> Santa Monica CA 90123 </p>
@@ -264,8 +316,16 @@
   }
 
   private static String getJsonValue(String regionCode, AddressDataKey key) {
+    return getJsonValue(regionCode, key, RegionDataConstants.getCountryFormatMap());
+  }
+
+  /**
+   * Visible for testing only.
+   */
+  static String getJsonValue(
+      String regionCode, AddressDataKey key, Map<String, String> regionDataMap) {
     Util.checkNotNull(regionCode);
-    String jsonString = RegionDataConstants.getCountryFormatMap().get(regionCode);
+    String jsonString = regionDataMap.get(regionCode);
     Util.checkNotNull(jsonString, "no json data for region code " + regionCode);
 
     try {
diff --git a/common/src/main/java/com/google/i18n/addressinput/common/RegionDataConstants.java b/common/src/main/java/com/google/i18n/addressinput/common/RegionDataConstants.java
index e3d24c8..f83b59a 100644
--- a/common/src/main/java/com/google/i18n/addressinput/common/RegionDataConstants.java
+++ b/common/src/main/java/com/google/i18n/addressinput/common/RegionDataConstants.java
@@ -1,1344 +1,282 @@
-/*
- * Copyright (C) 2010 Google Inc.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
+// Copyright (C) 2010 Google Inc.
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+//
 package com.google.i18n.addressinput.common;
 
-import org.json.JSONException;
-import org.json.JSONObject;
-
-import java.util.HashMap;
+import java.lang.String;
+import java.util.Collections;
 import java.util.Map;
+import java.util.TreeMap;
 
-/**
- * Initial data in JSON format for regions. This has some formatting information for some countries,
- * and a list of all the regions that the widget can support. Data has been sorted below for ease of
- * editing.
- */
-// TODO: Simplify this class to just use generated JSON strings (which will reduce its size a lot).
 public final class RegionDataConstants {
-  private static final Map<String, String> COUNTRY_FORMAT_MAP = new HashMap<String, String>();
+  private static final Map<String, String> addressDataMap = createMap();
 
-  private enum RegionDataEnum {
-    AC(new String[]{
-      "name", "ASCENSION ISLAND",
-    }),
-    AD(new String[]{
-      "name", "ANDORRA",
-      "lang", "ca",
-      "languages", "ca",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-    }),
-    AE(new String[]{
-      "name", "UNITED ARAB EMIRATES",
-      "lang", "ar",
-      "languages", "ar",
-      "fmt", "%N%n%O%n%A%n%S",
-      "lfmt", "%N%n%O%n%A%n%S",
-      "require", "AS",
-      "state_name_type", "emirate",
-    }),
-    AF(new String[]{
-      "name", "AFGHANISTAN",
-    }),
-    AG(new String[]{
-      "name", "ANTIGUA AND BARBUDA",
-      "require", "A",
-    }),
-    AI(new String[]{
-      "name", "ANGUILLA",
-    }),
-    AL(new String[]{
-      "name", "ALBANIA",
-    }),
-    AM(new String[]{
-      "name", "ARMENIA",
-      "lang", "hy",
-      "languages", "hy",
-      "fmt", "%N%n%O%n%A%n%Z%n%C%n%S",
-      "lfmt", "%N%n%O%n%A%n%Z%n%C%n%S",
-    }),
-    AO(new String[]{
-      "name", "ANGOLA",
-    }),
-    AQ(new String[]{
-      "name", "ANTARCTICA",
-    }),
-    AR(new String[]{
-      "name", "ARGENTINA",
-      "lang", "es",
-      "languages", "es",
-      "fmt", "%N%n%O%n%A%n%Z %C%n%S",
-      "upper", "ACZ",
-    }),
-    AS(new String[]{
-      "name", "AMERICAN SAMOA",
-      "fmt", "%N%n%O%n%A%n%C %S %Z",
-      "require", "ACSZ",
-      "upper", "ACNOS",
-      "zip_name_type", "zip",
-      "state_name_type", "state",
-    }),
-    AT(new String[]{
-      "name", "AUSTRIA",
-      "fmt", "%O%n%N%n%A%n%Z %C",
-      "require", "ACZ",
-    }),
-    AU(new String[]{
-      "name", "AUSTRALIA",
-      "lang", "en",
-      "languages", "en",
-      "fmt", "%O%n%N%n%A%n%C %S %Z",
-      "require", "ACSZ",
-      "upper", "CS",
-      "state_name_type", "state",
-    }),
-    AW(new String[]{
-      "name", "ARUBA",
-    }),
-    AX(new String[]{
-      "name", "FINLAND",
-      "fmt", "%O%n%N%n%A%nAX-%Z %C%n\u00C5LAND",
-      "require", "ACZ",
-      "postprefix", "AX-",
-    }),
-    AZ(new String[]{
-      "name", "AZERBAIJAN",
-      "fmt", "%N%n%O%n%A%nAZ %Z %C",
-      "postprefix", "AZ ",
-    }),
-    BA(new String[]{
-      "name", "BOSNIA AND HERZEGOVINA",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-    }),
-    BB(new String[]{
-      "name", "BARBADOS",
-      "state_name_type", "parish",
-    }),
-    BD(new String[]{
-      "name", "BANGLADESH",
-      "fmt", "%N%n%O%n%A%n%C - %Z",
-    }),
-    BE(new String[]{
-      "name", "BELGIUM",
-      "fmt", "%O%n%N%n%A%n%Z %C",
-      "require", "ACZ",
-    }),
-    BF(new String[]{
-      "name", "BURKINA FASO",
-      "fmt", "%N%n%O%n%A%n%C %X",
-    }),
-    BG(new String[]{
-      "name", "BULGARIA (REP.)",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-    }),
-    BH(new String[]{
-      "name", "BAHRAIN",
-      "fmt", "%N%n%O%n%A%n%C %Z",
-    }),
-    BI(new String[]{
-      "name", "BURUNDI",
-    }),
-    BJ(new String[]{
-      "name", "BENIN",
-      "upper", "AC",
-    }),
-    BL(new String[]{
-      "name", "SAINT BARTHELEMY",
-      "fmt", "%O%n%N%n%A%n%Z %C %X",
-      "upper", "ACX",
-      "require", "ACZ",
-    }),
-    BM(new String[]{
-      "name", "BERMUDA",
-      "fmt", "%N%n%O%n%A%n%C %Z",
-    }),
-    BN(new String[]{
-      "name", "BRUNEI DARUSSALAM",
-      "fmt", "%N%n%O%n%A%n%C %Z",
-    }),
-    BO(new String[]{
-      "name", "BOLIVIA",
-      "upper", "AC",
-    }),
-    BQ(new String[]{
-      "name", "BONAIRE, SINT EUSTATIUS, AND SABA",
-    }),
-    BR(new String[]{
-      "name", "BRAZIL",
-      "lang", "pt",
-      "languages", "pt",
-      "fmt", "%O%n%N%n%A%n%D%n%C-%S%n%Z",
-      "require", "ASCZ",
-      "upper", "CS",
-      "state_name_type", "state",
-      "sublocality_name_type", "neighborhood",
-    }),
-    BS(new String[]{
-      "name", "BAHAMAS",
-      "lang", "en",
-      "languages", "en",
-      "fmt", "%N%n%O%n%A%n%C, %S",
-      "state_name_type", "island",
-    }),
-    BT(new String[]{
-      "name", "BHUTAN",
-    }),
-    BV(new String[]{
-      "name", "BOUVET ISLAND",
-    }),
-    BW(new String[]{
-      "name", "BOTSWANA",
-    }),
-    BY(new String[]{
-      "name", "BELARUS",
-      "fmt", "%S%n%Z %C %X%n%A%n%O%n%N",
-    }),
-    BZ(new String[]{
-      "name", "BELIZE",
-    }),
-    CA(new String[]{
-      "name", "CANADA",
-      "lang", "en",
-      "languages", "en~fr",
-      "fmt", "%N%n%O%n%A%n%C %S %Z",
-      "require", "ACSZ",
-      "upper", "ACNOSZ",
-    }),
-    CC(new String[]{
-      "name", "COCOS (KEELING) ISLANDS",
-      "fmt", "%O%n%N%n%A%n%C %S %Z",
-      "upper", "CS",
-    }),
-    CD(new String[]{
-      "name", "CONGO (DEM. REP.)",
-      "fmt", "%N%n%O%n%A%n%C %X",
-    }),
-    CF(new String[]{
-      "name", "CENTRAL AFRICAN REPUBLIC",
-    }),
-    CG(new String[]{
-      "name", "CONGO (REP.)",
-    }),
-    CH(new String[]{
-      "name", "SWITZERLAND",
-      "lang", "de",
-      "languages", "de~fr~it",
-      "fmt", "%O%n%N%n%A%nCH-%Z %C",
-      "require", "ACZ",
-      "upper", "",
-      "postprefix", "CH-",
-    }),
-    CI(new String[]{
-      "name", "COTE D'IVOIRE",
-      "fmt", "%N%n%O%n%X %A %C %X",
-    }),
-    CK(new String[]{
-      "name", "COOK ISLANDS",
-    }),
-    CL(new String[]{
-      "name", "CHILE",
-      "lang", "es",
-      "languages", "es",
-      "fmt", "%N%n%O%n%A%n%Z %C%n%S",
-    }),
-    CM(new String[]{
-      "name", "CAMEROON",
-    }),
-    CN(new String[]{
-      "name", "CHINA",
-      "lang", "zh",
-      "languages", "zh",
-      "fmt", "%Z%n%S%C%D%n%A%n%O%n%N",
-      "lfmt", "%N%n%O%n%A%n%D%n%C%n%S, %Z",
-      "require", "ACSZ",
-      "upper", "S",
-      "sublocality_name_type", "district",
-    }),
-    CO(new String[]{
-      "name", "COLOMBIA",
-      "fmt", "%N%n%O%n%A%n%C, %S, %Z",
-      "state_name_type", "department",
-    }),
-    CR(new String[]{
-      "name", "COSTA RICA",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-    }),
-    CV(new String[]{
-      "name", "CAPE VERDE",
-      "lang", "pt",
-      "languages", "pt",
-      "fmt", "%N%n%O%n%A%n%Z %C%n%S",
-      "state_name_type", "island",
-    }),
-    CW(new String[]{
-      "name", "CURACAO",
-    }),
-    CX(new String[]{
-      "name", "CHRISTMAS ISLAND",
-      "fmt", "%O%n%N%n%A%n%C %S %Z",
-      "upper", "CS",
-    }),
-    CY(new String[]{
-      "name", "CYPRUS",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-    }),
-    CZ(new String[]{
-      "name", "CZECH REP.",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-    }),
-    DE(new String[]{
-      "name", "GERMANY",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-      "require", "ACZ",
-    }),
-    DJ(new String[]{
-      "name", "DJIBOUTI",
-    }),
-    DK(new String[]{
-      "name", "DENMARK",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-      "require", "ACZ",
-    }),
-    DM(new String[]{
-      "name", "DOMINICA",
-    }),
-    DO(new String[]{
-      "name", "DOMINICAN REP.",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-    }),
-    DZ(new String[]{
-      "name", "ALGERIA",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-    }),
-    EC(new String[]{
-      "name", "ECUADOR",
-      "fmt", "%N%n%O%n%A%n%Z%n%C",
-      "upper", "CZ",
-    }),
-    EE(new String[]{
-      "name", "ESTONIA",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-    }),
-    EG(new String[]{
-      "name", "EGYPT",
-      "lang", "ar",
-      "languages", "ar",
-      "fmt", "%N%n%O%n%A%n%C%n%S%n%Z",
-      "lfmt", "%N%n%O%n%A%n%C%n%S%n%Z",
-    }),
-    EH(new String[]{
-      "name", "WESTERN SAHARA",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-    }),
-    ER(new String[]{
-      "name", "ERITREA",
-    }),
-    ES(new String[]{
-      "name", "SPAIN",
-      "lang", "es",
-      "languages", "es",
-      "fmt", "%N%n%O%n%A%n%Z %C %S",
-      "require", "ACSZ",
-      "upper", "CS",
-    }),
-    ET(new String[]{
-      "name", "ETHIOPIA",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-    }),
-    FI(new String[]{
-      "name", "FINLAND",
-      "fmt", "%O%n%N%n%A%nFI-%Z %C",
-      "require", "ACZ",
-      "postprefix", "FI-",
-    }),
-    FJ(new String[]{
-      "name", "FIJI",
-    }),
-    FK(new String[]{
-      "name", "FALKLAND ISLANDS (MALVINAS)",
-      "fmt", "%N%n%O%n%A%n%X%n%C%n%Z",
-      "require", "ACZ",
-      "upper", "CZ",
-    }),
-    FM(new String[]{
-      "name", "MICRONESIA (Federated State of)",
-      "fmt", "%N%n%O%n%A%n%C %S %Z",
-      "require", "ACSZ",
-      "upper", "ACNOS",
-      "zip_name_type", "zip",
-      "state_name_type", "state",
-    }),
-    FO(new String[]{
-      "name", "FAROE ISLANDS",
-      "fmt", "%N%n%O%n%A%nFO%Z %C",
-      "postprefix", "FO",
-    }),
-    FR(new String[]{
-      "name", "FRANCE",
-      "fmt", "%O%n%N%n%A%n%Z %C %X",
-      "require", "ACZ",
-      "upper", "CX",
-    }),
-    GA(new String[]{
-      "name", "GABON",
-    }),
-    GB(new String[]{
-      "name", "UNITED KINGDOM",
-      "fmt", "%N%n%O%n%A%n%C%n%S%n%Z",
-      "require", "ACZ",
-      "upper", "CZ",
-      "state_name_type", "county",
-      "locality_name_type", "post_town",
-    }),
-    GD(new String[]{
-      "name", "GRENADA (WEST INDIES)",
-    }),
-    GE(new String[]{
-      "name", "GEORGIA",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-    }),
-    GF(new String[]{
-      "name", "FRENCH GUIANA",
-      "fmt", "%O%n%N%n%A%n%Z %C %X",
-      "require", "ACZ",
-      "upper", "ACX",
-    }),
-    GG(new String[]{
-      "name", "CHANNEL ISLANDS",
-      "fmt", "%N%n%O%n%A%n%X%n%C%nGUERNSEY%n%Z",
-      "require", "ACZ",
-      "upper", "CZ",
-    }),
-    GH(new String[]{
-      "name", "GHANA",
-    }),
-    GI(new String[]{
-      "name", "GIBRALTAR",
-      "fmt", "%N%n%O%n%A%nGIBRALTAR%n%Z",
-      "require", "A",
-    }),
-    GL(new String[]{
-      "name", "GREENLAND",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-      "require", "ACZ",
-    }),
-    GM(new String[]{
-      "name", "GAMBIA",
-    }),
-    GN(new String[]{
-      "name", "GUINEA",
-      "fmt", "%N%n%O%n%Z %A %C",
-    }),
-    GP(new String[]{
-      "name", "GUADELOUPE",
-      "fmt", "%O%n%N%n%A%n%Z %C %X",
-      "require", "ACZ",
-      "upper", "ACX",
-    }),
-    GQ(new String[]{
-      "name", "EQUATORIAL GUINEA",
-    }),
-    GR(new String[]{
-      "name", "GREECE",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-      "require", "ACZ",
-    }),
-    GS(new String[]{
-      "name", "SOUTH GEORGIA",
-      "fmt", "%N%n%O%n%A%n%X%n%C%n%Z",
-      "require", "ACZ",
-      "upper", "CZ",
-    }),
-    GT(new String[]{
-      "name", "GUATEMALA",
-      "fmt", "%N%n%O%n%A%n%Z- %C",
-    }),
-    GU(new String[]{
-      "name", "GUAM",
-      "fmt", "%N%n%O%n%A%n%C %S %Z",
-      "require", "ACSZ",
-      "upper", "ACNOS",
-      "zip_name_type", "zip",
-      "state_name_type", "state",
-    }),
-    GW(new String[]{
-      "name", "GUINEA-BISSAU",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-    }),
-    GY(new String[]{
-      "name", "GUYANA",
-    }),
-    HK(new String[]{
-      "name", "HONG KONG",
-      "lang", "zh-Hant",
-      "languages", "zh-Hant~en",
-      "fmt", "%S%n%C%n%A%n%O%n%N",
-      "lfmt", "%N%n%O%n%A%n%C%n%S",
-      "require", "AS",
-      "upper", "S",
-      "state_name_type", "area",
-      "locality_name_type", "district",
-    }),
-    HM(new String[]{
-      "name", "HEARD AND MCDONALD ISLANDS",
-      "fmt", "%O%n%N%n%A%n%C %S %Z",
-      "upper", "CS",
-    }),
-    HN(new String[]{
-      "name", "HONDURAS",
-      "fmt", "%N%n%O%n%A%n%C, %S%n%Z",
-      "require", "ACS",
-    }),
-    HR(new String[]{
-      "name", "CROATIA",
-      "fmt", "%N%n%O%n%A%nHR-%Z %C",
-      "postprefix", "HR-",
-    }),
-    HT(new String[]{
-      "name", "HAITI",
-      "fmt", "%N%n%O%n%A%nHT%Z %C %X",
-      "postprefix", "HT",
-    }),
-    HU(new String[]{
-      "name", "HUNGARY (Rep.)",
-      "fmt", "%N%n%O%n%C%n%A%n%Z",
-      "upper", "ACNO",
-    }),
-    ID(new String[]{
-      "name", "INDONESIA",
-      "lang", "id",
-      "languages", "id",
-      "fmt", "%N%n%O%n%A%n%C%n%S %Z",
-    }),
-    IE(new String[]{
-      "name", "IRELAND",
-      "lang", "en",
-      "languages", "en",
-      "fmt", "%N%n%O%n%A%n%C%n%S",
-      "state_name_type", "county",
-    }),
-    IL(new String[]{
-      "name", "ISRAEL",
-      "fmt", "%N%n%O%n%A%n%C %Z",
-    }),
-    IM(new String[]{
-      "name", "ISLE OF MAN",
-      "fmt", "%N%n%O%n%A%n%X%n%C%n%Z",
-      "require", "ACZ",
-      "upper", "CZ",
-    }),
-    IN(new String[]{
-      "name", "INDIA",
-      "lang", "en",
-      "languages", "en",
-      "fmt", "%N%n%O%n%A%n%C %Z%n%S",
-      "require", "ACSZ",
-      "zip_name_type", "pin",
-      "state_name_type", "state",
-    }),
-    IO(new String[]{
-      "name", "BRITISH INDIAN OCEAN TERRITORY",
-      "fmt", "%N%n%O%n%A%n%X%n%C%n%Z",
-      "require", "ACZ",
-      "upper", "CZ",
-    }),
-    IQ(new String[]{
-      "name", "IRAQ",
-      "fmt", "%O%n%N%n%A%n%C, %S%n%Z",
-      "require", "ACS",
-      "upper", "CS",
-    }),
-    IR(new String[]{
-      "name", "IRAN",
-      "fmt", "%O%n%N%n%S%n%C, %D%n%A%n%Z",
-      "sublocality_name_type", "neighborhood",
-    }),
-    IS(new String[]{
-      "name", "ICELAND",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-    }),
-    IT(new String[]{
-      "name", "ITALY",
-      "lang", "it",
-      "languages", "it",
-      "fmt", "%N%n%O%n%A%n%Z %C %S",
-      "require", "ACSZ",
-      "upper", "CS",
-    }),
-    JE(new String[]{
-      "name", "CHANNEL ISLANDS",
-      "fmt", "%N%n%O%n%A%n%X%n%C%nJERSEY%n%Z",
-      "require", "ACZ",
-      "upper", "CZ",
-    }),
-    JM(new String[]{
-      "name", "JAMAICA",
-      "lang", "en",
-      "languages", "en",
-      "fmt", "%N%n%O%n%A%n%C%n%S %X",
-      "require", "ACS",
-      "state_name_type", "parish",
-    }),
-    JO(new String[]{
-      "name", "JORDAN",
-      "fmt", "%N%n%O%n%A%n%C %Z",
-    }),
-    JP(new String[]{
-      "name", "JAPAN",
-      "lang", "ja",
-      "languages", "ja",
-      "fmt", "\u3012%Z%n%S%C%n%A%n%O%n%N",
-      "lfmt", "%N%n%O%n%A%n%C, %S%n%Z",
-      "require", "ACSZ",
-      "upper", "S",
-      "state_name_type", "prefecture",
-    }),
-    KE(new String[]{
-      "name", "KENYA",
-      "fmt", "%N%n%O%n%A%n%C%n%Z",
-    }),
-    KG(new String[]{
-      "name", "KYRGYZSTAN",
-      "fmt", "%Z %C %X%n%A%n%O%n%N",
-    }),
-    KH(new String[]{
-      "name", "CAMBODIA",
-      "fmt", "%N%n%O%n%A%n%C %Z",
-    }),
-    KI(new String[]{
-      "name", "KIRIBATI",
-      "fmt", "%N%n%O%n%A%n%S%n%C",
-      "upper", "ACNOS",
-      "state_name_type", "island",
-    }),
-    KM(new String[]{
-      "name", "COMOROS",
-      "upper", "AC",
-    }),
-    KN(new String[]{
-      "name", "SAINT KITTS AND NEVIS",
-      "lang", "en",
-      "languages", "en",
-      "fmt", "%N%n%O%n%A%n%C, %S",
-      "require", "ACS",
-      "state_name_type", "island",
-    }),
-    KR(new String[]{
-      "name", "SOUTH KOREA",
-      "lang", "ko",
-      "languages", "ko",
-      "fmt", "%S %C%D%n%A%n%O%n%N%n%Z",
-      "lfmt", "%N%n%O%n%A%n%D%n%C%n%S%n%Z",
-      "require", "ACSZ",
-      "upper", "Z",
-      "state_name_type", "do_si",
-      "sublocality_name_type", "district",
-    }),
-    KW(new String[]{
-      "name", "KUWAIT",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-    }),
-    KY(new String[]{
-      "name", "CAYMAN ISLANDS",
-      "lang", "en",
-      "languages", "en",
-      "fmt", "%N%n%O%n%A%n%S %Z",
-      "require", "AS",
-      "state_name_type", "island",
-    }),
-    KZ(new String[]{
-      "name", "KAZAKHSTAN",
-      "fmt", "%Z%n%S%n%C%n%A%n%O%n%N",
-    }),
-    LA(new String[]{
-      "name", "LAO (PEOPLE'S DEM. REP.)",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-    }),
-    LB(new String[]{
-      "name", "LEBANON",
-      "fmt", "%N%n%O%n%A%n%C %Z",
-    }),
-    LC(new String[]{
-      "name", "SAINT LUCIA",
-    }),
-    LI(new String[]{
-      "name", "LIECHTENSTEIN",
-      "fmt", "%O%n%N%n%A%nFL-%Z %C",
-      "require", "ACZ",
-      "postprefix", "FL-",
-    }),
-    LK(new String[]{
-      "name", "SRI LANKA",
-      "fmt", "%N%n%O%n%A%n%C%n%Z",
-    }),
-    LR(new String[]{
-      "name", "LIBERIA",
-      "fmt", "%N%n%O%n%A%n%Z %C %X",
-    }),
-    LS(new String[]{
-      "name", "LESOTHO",
-      "fmt", "%N%n%O%n%A%n%C %Z",
-    }),
-    LT(new String[]{
-      "name", "LITHUANIA",
-      "fmt", "%O%n%N%n%A%nLT-%Z %C",
-      "postprefix", "LT-",
-    }),
-    LU(new String[]{
-      "name", "LUXEMBOURG",
-      "fmt", "%O%n%N%n%A%nL-%Z %C",
-      "require", "ACZ",
-      "postprefix", "L-",
-    }),
-    LV(new String[]{
-      "name", "LATVIA",
-      "fmt", "%N%n%O%n%A%n%C, %Z",
-    }),
-    LY(new String[]{
-      "name", "LIBYA",
-    }),
-    MA(new String[]{
-      "name", "MOROCCO",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-    }),
-    MC(new String[]{
-      "name", "MONACO",
-      "fmt", "%N%n%O%n%A%nMC-%Z %C %X",
-      "postprefix", "MC-",
-    }),
-    MD(new String[]{
-      "name", "Rep. MOLDOVA",
-      "fmt", "%N%n%O%n%A%nMD-%Z %C",
-      "postprefix", "MD-",
-    }),
-    ME(new String[]{
-      "name", "MONTENEGRO",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-    }),
-    MF(new String[]{
-      "name", "SAINT MARTIN",
-      "fmt", "%O%n%N%n%A%n%Z %C %X",
-      "upper", "ACX",
-      "require", "ACZ",
-    }),
-    MG(new String[]{
-      "name", "MADAGASCAR",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-    }),
-    MH(new String[]{
-      "name", "MARSHALL ISLANDS",
-      "fmt", "%N%n%O%n%A%n%C %S %Z",
-      "require", "ACSZ",
-      "upper", "ACNOS",
-      "zip_name_type", "zip",
-      "state_name_type", "state",
-    }),
-    MK(new String[]{
-      "name", "MACEDONIA",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-    }),
-    ML(new String[]{
-      "name", "MALI",
-    }),
-    MM(new String[]{
-      "name", "MYANMAR",
-      "fmt", "%N%n%O%n%A%n%C, %Z",
-    }),
-    MN(new String[]{
-      "name", "MONGOLIA",
-      "fmt", "%N%n%O%n%A%n%S %C-%X%n%Z",
-    }),
-    MO(new String[]{
-      "name", "MACAO",
-      "lang", "zh-Hant",
-      "languages", "zh-Hant",
-      "fmt", "%A%n%O%n%N",
-      "lfmt", "%N%n%O%n%A",
-      "require", "A",
-    }),
-    MP(new String[]{
-      "name", "NORTHERN MARIANA ISLANDS",
-      "fmt", "%N%n%O%n%A%n%C %S %Z",
-      "require", "ACSZ",
-      "upper", "ACNOS",
-      "zip_name_type", "zip",
-      "state_name_type", "state",
-    }),
-    MQ(new String[]{
-      "name", "MARTINIQUE",
-      "fmt", "%O%n%N%n%A%n%Z %C %X",
-      "require", "ACZ",
-      "upper", "ACX",
-    }),
-    MR(new String[]{
-      "name", "MAURITANIA",
-      "upper", "AC",
-    }),
-    MS(new String[]{
-      "name", "MONTSERRAT",
-    }),
-    MT(new String[]{
-      "name", "MALTA",
-      "fmt", "%N%n%O%n%A%n%C %Z",
-      "upper", "CZ",
-    }),
-    MU(new String[]{
-      "name", "MAURITIUS",
-      "fmt", "%N%n%O%n%A%n%Z%n%C",
-      "upper", "CZ",
-    }),
-    MV(new String[]{
-      "name", "MALDIVES",
-      "fmt", "%N%n%O%n%A%n%C %Z",
-    }),
-    MW(new String[]{
-      "name", "MALAWI",
-      "fmt", "%N%n%O%n%A%n%C %X",
-    }),
-    MX(new String[]{
-      "name", "MEXICO",
-      "lang", "es",
-      "languages", "es",
-      "fmt", "%N%n%O%n%A%n%D%n%Z %C, %S",
-      "require", "ACZ",
-      "upper", "CSZ",
-      "state_name_type", "state",
-      "sublocality_name_type", "neighborhood",
-    }),
-    MY(new String[]{
-      "name", "MALAYSIA",
-      "lang", "ms",
-      "languages", "ms",
-      "fmt", "%N%n%O%n%A%n%D%n%Z %C%n%S",
-      "require", "ACZ",
-      "upper", "CS",
-      "state_name_type", "state",
-      "sublocality_name_type", "village_township",
-    }),
-    MZ(new String[]{
-      "name", "MOZAMBIQUE",
-    }),
-    NA(new String[]{
-      "name", "NAMIBIA",
-    }),
-    NC(new String[]{
-      "name", "NEW CALEDONIA",
-      "fmt", "%O%n%N%n%A%n%Z %C %X",
-      "require", "ACZ",
-      "upper", "ACX",
-    }),
-    NE(new String[]{
-      "name", "NIGER",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-    }),
-    NF(new String[]{
-      "name", "NORFOLK ISLAND",
-      "fmt", "%O%n%N%n%A%n%C %S %Z",
-      "upper", "CS",
-    }),
-    NG(new String[]{
-      "name", "NIGERIA",
-      "lang", "en",
-      "languages", "en",
-      "fmt", "%N%n%O%n%A%n%C %Z%n%S",
-      "upper", "CS",
-      "state_name_type", "state",
-    }),
-    NI(new String[]{
-      "name", "NICARAGUA",
-      "lang", "es",
-      "languages", "es",
-      "fmt", "%N%n%O%n%A%n%Z%n%C, %S",
-      "upper", "CS",
-      "state_name_type", "department",
-    }),
-    NL(new String[]{
-      "name", "NETHERLANDS",
-      "fmt", "%O%n%N%n%A%n%Z %C",
-      "require", "ACZ",
-    }),
-    NO(new String[]{
-      "name", "NORWAY",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-      "require", "ACZ",
-    }),
-    NP(new String[]{
-      "name", "NEPAL",
-      "fmt", "%N%n%O%n%A%n%C %Z",
-    }),
-    NR(new String[]{
-      "name", "NAURU CENTRAL PACIFIC",
-      "lang", "en",
-      "languages", "en",
-      "fmt", "%N%n%O%n%A%n%S",
-      "require", "AS",
-      "state_name_type", "district",
-    }),
-    NU(new String[]{
-      "name", "NIUE",
-    }),
-    NZ(new String[]{
-      "name", "NEW ZEALAND",
-      "fmt", "%N%n%O%n%A%n%D%n%C %Z",
-      "require", "ACZ",
-    }),
-    OM(new String[]{
-      "name", "OMAN",
-      "fmt", "%N%n%O%n%A%n%Z%n%C",
-    }),
-    PA(new String[]{
-      "name", "PANAMA (REP.)",
-      "fmt", "%N%n%O%n%A%n%C%n%S",
-      "upper", "CS",
-    }),
-    PE(new String[]{
-      "name", "PERU",
-    }),
-    PF(new String[]{
-      "name", "FRENCH POLYNESIA",
-      "fmt", "%N%n%O%n%A%n%Z %C %S",
-      "require", "ACSZ",
-      "upper", "CS",
-      "state_name_type", "island",
-    }),
-    PG(new String[]{
-      "name", "PAPUA NEW GUINEA",
-      "fmt", "%N%n%O%n%A%n%C %Z %S",
-      "require", "ACS",
-    }),
-    PH(new String[]{
-      "name", "PHILIPPINES",
-      "lang", "en",
-      "languages", "en",
-      "fmt", "%N%n%O%n%A%n%D, %C%n%Z %S",
-      "require", "AC",
-    }),
-    PK(new String[]{
-      "name", "PAKISTAN",
-      "fmt", "%N%n%O%n%A%n%C-%Z",
-    }),
-    PL(new String[]{
-      "name", "POLAND",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-      "require", "ACZ",
-    }),
-    PM(new String[]{
-      "name", "ST. PIERRE AND MIQUELON",
-      "fmt", "%O%n%N%n%A%n%Z %C %X",
-      "require", "ACZ",
-      "upper", "ACX",
-    }),
-    PN(new String[]{
-      "name", "PITCAIRN",
-      "fmt", "%N%n%O%n%A%n%X%n%C%n%Z",
-      "require", "ACZ",
-      "upper", "CZ",
-    }),
-    PR(new String[]{
-      "name", "PUERTO RICO",
-      "fmt", "%N%n%O%n%A%n%C PR %Z",
-      "require", "ACZ",
-      "upper", "ACNO",
-      "zip_name_type", "zip",
-      "postprefix", "PR",
-    }),
-    PS(new String[]{
-      "name", "PALESTINIAN TERRITORY",
-    }),
-    PT(new String[]{
-      "name", "PORTUGAL",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-      "require", "ACZ",
-    }),
-    PW(new String[]{
-      "name", "PALAU",
-      "fmt", "%N%n%O%n%A%n%C %S %Z",
-      "require", "ACSZ",
-      "upper", "ACNOS",
-      "zip_name_type", "zip",
-      "state_name_type", "state",
-    }),
-    PY(new String[]{
-      "name", "PARAGUAY",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-    }),
-    QA(new String[]{
-      "name", "QATAR",
-      "upper", "AC",
-    }),
-    RE(new String[]{
-      "name", "REUNION",
-      "fmt", "%O%n%N%n%A%n%Z %C %X",
-      "require", "ACZ",
-      "upper", "ACX",
-    }),
-    RO(new String[]{
-      "name", "ROMANIA",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-      "upper", "AC",
-    }),
-    RS(new String[]{
-      "name", "REPUBLIC OF SERBIA",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-    }),
-    RU(new String[]{
-      "name", "RUSSIAN FEDERATION",
-      "lang", "ru",
-      "languages", "ru",
-      "fmt", "%N%n%O%n%A%n%C%n%S%n%Z",
-      "lfmt", "%N%n%O%n%A%n%C%n%S%n%Z",
-      "require", "ACZ",
-      "upper", "AC",
-      "state_name_type", "oblast",
-    }),
-    RW(new String[]{
-      "name", "RWANDA",
-      "upper", "AC",
-    }),
-    SA(new String[]{
-      "name", "SAUDI ARABIA",
-      "fmt", "%N%n%O%n%A%n%C %Z",
-    }),
-    SB(new String[]{
-      "name", "SOLOMON ISLANDS",
-    }),
-    SC(new String[]{
-      "name", "SEYCHELLES",
-      "fmt", "%N%n%O%n%A%n%C%n%S",
-      "upper", "S",
-      "state_name_type", "island",
-    }),
-    SE(new String[]{
-      "name", "SWEDEN",
-      "fmt", "%O%n%N%n%A%nSE-%Z %C",
-      "require", "ACZ",
-      "postprefix", "SE-",
-    }),
-    SG(new String[]{
-      "name", "REP. OF SINGAPORE",
-      "fmt", "%N%n%O%n%A%nSINGAPORE %Z",
-      "require", "AZ",
-    }),
-    SH(new String[]{
-      "name", "SAINT HELENA",
-      "fmt", "%N%n%O%n%A%n%X%n%C%n%Z",
-      "require", "ACZ",
-      "upper", "CZ",
-    }),
-    SI(new String[]{
-      "name", "SLOVENIA",
-      "fmt", "%N%n%O%n%A%nSI- %Z %C",
-      "postprefix", "SI-",
-    }),
-    SJ(new String[]{
-      "name", "SVALBARD AND JAN MAYEN ISLANDS",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-      "require", "ACZ",
-    }),
-    SK(new String[]{
-      "name", "SLOVAKIA",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-    }),
-    SL(new String[]{
-      "name", "SIERRA LEONE",
-    }),
-    SM(new String[]{
-      "name", "SAN MARINO",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-      "require", "AZ",
-    }),
-    SN(new String[]{
-      "name", "SENEGAL",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-    }),
-    SO(new String[]{
-      "name", "SOMALIA",
-      "lang", "so",
-      "languages", "so",
-      "fmt", "%N%n%O%n%A%n%C, %S %Z",
-      "require", "ACS",
-      "upper", "ACS",
-    }),
-    SR(new String[]{
-      "name", "SURINAME",
-      "lang", "nl",
-      "languages", "nl",
-      "fmt", "%N%n%O%n%A%n%C %X%n%S",
-      "upper", "AS",
-    }),
-    SS(new String[]{
-      "name", "SOUTH SUDAN",
-    }),
-    ST(new String[]{
-      "name", "SAO TOME AND PRINCIPE",
-      "fmt", "%N%n%O%n%A%n%C %X",
-    }),
-    SV(new String[]{
-      "name", "EL SALVADOR",
-      "lang", "es",
-      "languages", "es",
-      "fmt", "%N%n%O%n%A%n%Z-%C%n%S",
-      "require", "ACS",
-      "upper", "CSZ",
-    }),
-    SX(new String[]{
-      "name", "SINT MAARTEN",
-    }),
-    SZ(new String[]{
-      "name", "SWAZILAND",
-      "fmt", "%N%n%O%n%A%n%C%n%Z",
-      "upper", "ACZ",
-    }),
-    TA(new String[]{
-      "name", "TRISTAN DA CUNHA",
-    }),
-    TC(new String[]{
-      "name", "TURKS AND CAICOS ISLANDS",
-      "fmt", "%N%n%O%n%A%n%X%n%C%n%Z",
-      "require", "ACZ",
-      "upper", "CZ",
-    }),
-    TD(new String[]{
-      "name", "CHAD",
-    }),
-    TF(new String[]{
-      "name", "FRENCH SOUTHERN TERRITORIES",
-    }),
-    TG(new String[]{
-      "name", "TOGO",
-    }),
-    TH(new String[]{
-      "name", "THAILAND",
-      "lang", "th",
-      "languages", "th",
-      "fmt", "%N%n%O%n%A%n%D %C%n%S %Z",
-      "lfmt", "%N%n%O%n%A%n%D, %C%n%S %Z",
-      "upper", "S",
-    }),
-    TJ(new String[]{
-      "name", "TAJIKISTAN",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-    }),
-    TK(new String[]{
-      "name", "TOKELAU",
-    }),
-    TL(new String[]{
-      "name", "TIMOR-LESTE",
-    }),
-    TM(new String[]{
-      "name", "TURKMENISTAN",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-    }),
-    TN(new String[]{
-      "name", "TUNISIA",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-    }),
-    TO(new String[]{
-      "name", "TONGA",
-    }),
-    TR(new String[]{
-      "name", "TURKEY",
-      "lang", "tr",
-      "languages", "tr",
-      "fmt", "%N%n%O%n%A%n%Z %C/%S",
-      "require", "ACZ",
-      "locality_name_type", "district",
-    }),
-    TT(new String[]{
-      "name", "TRINIDAD AND TOBAGO",
-    }),
-    TV(new String[]{
-      "name", "TUVALU",
-      "lang", "tyv",
-      "languages", "tyv",
-      "fmt", "%N%n%O%n%A%n%X%n%C%n%S",
-      "upper", "ACS",
-      "state_name_type", "island",
-    }),
-    TW(new String[]{
-      "name", "TAIWAN",
-      "lang", "zh-Hant",
-      "languages", "zh-Hant",
-      "fmt", "%Z%n%S%C%n%A%n%O%n%N",
-      "lfmt", "%N%n%O%n%A%n%C, %S %Z",
-      "require", "ACSZ",
-      "state_name_type", "county",
-    }),
-    TZ(new String[]{
-      "name", "TANZANIA (UNITED REP.)",
-    }),
-    UA(new String[]{
-      "name", "UKRAINE",
-      "lang", "uk",
-      "languages", "uk",
-      "fmt", "%N%n%O%n%A%n%C%n%S%n%Z",
-      "lfmt", "%N%n%O%n%A%n%C%n%S%n%Z",
-      "require", "ACZ",
-      "state_name_type", "oblast",
-    }),
-    UG(new String[]{
-      "name", "UGANDA",
-    }),
-    UM(new String[]{
-      "name", "UNITED STATES MINOR OUTLYING ISLANDS",
-      "fmt", "%N%n%O%n%A%n%C %S %Z",
-      "require", "ACS",
-      "upper", "ACNOS",
-      "zip_name_type", "zip",
-      "state_name_type", "state",
-    }),
-    US(new String[]{
-      "name", "UNITED STATES",
-      "lang", "en",
-      "languages", "en",
-      "fmt", "%N%n%O%n%A%n%C, %S %Z",
-      "require", "ACSZ",
-      "upper", "CS",
-      "zip_name_type", "zip",
-      "state_name_type", "state",
-    }),
-    UY(new String[]{
-      "name", "URUGUAY",
-      "lang", "es",
-      "languages", "es",
-      "fmt", "%N%n%O%n%A%n%Z %C %S",
-      "upper", "CS",
-    }),
-    UZ(new String[]{
-      "name", "UZBEKISTAN",
-      "fmt", "%N%n%O%n%A%n%Z %C%n%S",
-      "upper", "CS",
-    }),
-    VA(new String[]{
-      "name", "VATICAN",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-    }),
-    VC(new String[]{
-      "name", "SAINT VINCENT AND THE GRENADINES (ANTILLES)",
-    }),
-    VE(new String[]{
-      "name", "VENEZUELA",
-      "lang", "es",
-      "languages", "es",
-      "fmt", "%N%n%O%n%A%n%C %Z, %S",
-      "require", "ACS",
-      "upper", "CS",
-    }),
-    VG(new String[]{
-      "name", "VIRGIN ISLANDS (BRITISH)",
-      "fmt", "%N%n%O%n%A%n%C%n%Z",
-      "require", "A",
-    }),
-    VI(new String[]{
-      "name", "VIRGIN ISLANDS (U.S.)",
-      "fmt", "%N%n%O%n%A%n%C %S %Z",
-      "require", "ACSZ",
-      "upper", "ACNOS",
-      "zip_name_type", "zip",
-      "state_name_type", "state",
-    }),
-    VN(new String[]{
-      "name", "VIET NAM",
-      "lang", "vi",
-      "languages", "vi",
-      "fmt", "%N%n%O%n%A%n%C%n%S %Z",
-      "lfmt", "%N%n%O%n%A%n%C%n%S %Z",
-    }),
-    VU(new String[]{
-      "name", "VANUATU",
-    }),
-    WF(new String[]{
-      "name", "WALLIS AND FUTUNA ISLANDS",
-      "fmt", "%O%n%N%n%A%n%Z %C %X",
-      "require", "ACZ",
-      "upper", "ACX",
-    }),
-    WS(new String[]{
-      "name", "SAMOA",
-    }),
-    XK(new String[]{
-      "name", "KOSOVO",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-    }),
-    YE(new String[]{
-      "name", "YEMEN",
-    }),
-    YT(new String[]{
-      "name", "MAYOTTE",
-      "fmt", "%O%n%N%n%A%n%Z %C %X",
-      "require", "ACZ",
-      "upper", "ACX",
-    }),
-    ZA(new String[]{
-      "name", "SOUTH AFRICA",
-      "fmt", "%N%n%O%n%A%n%D%n%C%n%Z",
-      "require", "ACZ",
-    }),
-    ZM(new String[]{
-      "name", "ZAMBIA",
-      "fmt", "%N%n%O%n%A%n%Z %C",
-    }),
-    ZW(new String[]{
-      "name", "ZIMBABWE",
-    }),
-    ZZ(new String[]{
-      "fmt", "%N%n%O%n%A%n%C",
-      "require", "AC",
-      "upper", "C",
-      "zip_name_type", "postal",
-      "state_name_type", "province",
-      "locality_name_type", "city",
-      "sublocality_name_type", "suburb",
-    });
-
-    private String jsonString;
-
-    private RegionDataEnum(String[] inputArray) {
-      jsonString = convertArrayToJsonString(inputArray);
-    }
-
-    String getJsonString() {
-      return jsonString;
-    }
+  public static Map<String, String> getCountryFormatMap() {
+    return addressDataMap;
   }
 
-  static {
-    for (RegionDataEnum region : RegionDataEnum.values()) {
-      COUNTRY_FORMAT_MAP.put(region.toString(), region.getJsonString());
-    }
-  }
-
-  static Map<String, String> getCountryFormatMap() {
-    return COUNTRY_FORMAT_MAP;
-  }
-
-  /**
-   * Assumes the array is a well-formed array - i.e., there are no unmatched keys in the input.
-   * Package-private so it can be accessed by tests.
-   */
-  static String convertArrayToJsonString(String[] input) {
-    // TODO(user): Consider using just a StringBuilder here.
-    JSONObject object = new JSONObject();
-    for (int i = 0; i < input.length; i += 2) {
-      try {
-        object.put(input[i], input[i + 1]);
-      } catch (JSONException e) {
-        // Ignore for now.
-      }
-    }
-    return object.toString();
+  private static Map<String, String> createMap() {
+    TreeMap<String, String> map = new TreeMap<String, String>();
+    map.put("AC", "{\"name\":\"ASCENSION ISLAND\"}");
+    map.put("AD", "{\"name\":\"ANDORRA\",\"lang\":\"ca\",\"languages\":\"ca\",\"fmt\":\"%N%n%O%n%A%n%Z %C\"}");
+    map.put("AE", "{\"name\":\"UNITED ARAB EMIRATES\",\"lang\":\"ar\",\"languages\":\"ar\",\"lfmt\":\"%N%n%O%n%A%n%S\",\"fmt\":\"%N%n%O%n%A%n%S\",\"require\":\"AS\",\"state_name_type\":\"emirate\"}");
+    map.put("AF", "{\"name\":\"AFGHANISTAN\"}");
+    map.put("AG", "{\"name\":\"ANTIGUA AND BARBUDA\",\"require\":\"A\"}");
+    map.put("AI", "{\"name\":\"ANGUILLA\"}");
+    map.put("AL", "{\"name\":\"ALBANIA\"}");
+    map.put("AM", "{\"name\":\"ARMENIA\",\"lang\":\"hy\",\"languages\":\"hy\",\"lfmt\":\"%N%n%O%n%A%n%Z%n%C%n%S\",\"fmt\":\"%N%n%O%n%A%n%Z%n%C%n%S\"}");
+    map.put("AO", "{\"name\":\"ANGOLA\"}");
+    map.put("AQ", "{\"name\":\"ANTARCTICA\"}");
+    map.put("AR", "{\"name\":\"ARGENTINA\",\"lang\":\"es\",\"languages\":\"es\",\"fmt\":\"%N%n%O%n%A%n%Z %C%n%S\",\"upper\":\"ACZ\"}");
+    map.put("AS", "{\"name\":\"AMERICAN SAMOA\",\"fmt\":\"%N%n%O%n%A%n%C %S %Z\",\"require\":\"ACSZ\",\"upper\":\"ACNOS\",\"state_name_type\":\"state\",\"zip_name_type\":\"zip\"}");
+    map.put("AT", "{\"name\":\"AUSTRIA\",\"fmt\":\"%O%n%N%n%A%n%Z %C\",\"require\":\"ACZ\"}");
+    map.put("AU", "{\"name\":\"AUSTRALIA\",\"lang\":\"en\",\"languages\":\"en\",\"fmt\":\"%O%n%N%n%A%n%C %S %Z\",\"require\":\"ACSZ\",\"upper\":\"CS\",\"state_name_type\":\"state\"}");
+    map.put("AW", "{\"name\":\"ARUBA\"}");
+    map.put("AX", "{\"name\":\"FINLAND\",\"fmt\":\"%O%n%N%n%A%nAX-%Z %C%nÅLAND\",\"require\":\"ACZ\",\"postprefix\":\"AX-\"}");
+    map.put("AZ", "{\"name\":\"AZERBAIJAN\",\"fmt\":\"%N%n%O%n%A%nAZ %Z %C\",\"postprefix\":\"AZ \"}");
+    map.put("BA", "{\"name\":\"BOSNIA AND HERZEGOVINA\",\"fmt\":\"%N%n%O%n%A%n%Z %C\"}");
+    map.put("BB", "{\"name\":\"BARBADOS\",\"state_name_type\":\"parish\"}");
+    map.put("BD", "{\"name\":\"BANGLADESH\",\"fmt\":\"%N%n%O%n%A%n%C - %Z\"}");
+    map.put("BE", "{\"name\":\"BELGIUM\",\"fmt\":\"%O%n%N%n%A%n%Z %C\",\"require\":\"ACZ\"}");
+    map.put("BF", "{\"name\":\"BURKINA FASO\",\"fmt\":\"%N%n%O%n%A%n%C %X\"}");
+    map.put("BG", "{\"name\":\"BULGARIA (REP.)\",\"fmt\":\"%N%n%O%n%A%n%Z %C\"}");
+    map.put("BH", "{\"name\":\"BAHRAIN\",\"fmt\":\"%N%n%O%n%A%n%C %Z\"}");
+    map.put("BI", "{\"name\":\"BURUNDI\"}");
+    map.put("BJ", "{\"name\":\"BENIN\",\"upper\":\"AC\"}");
+    map.put("BL", "{\"name\":\"SAINT BARTHELEMY\",\"fmt\":\"%O%n%N%n%A%n%Z %C %X\",\"require\":\"ACZ\",\"upper\":\"ACX\"}");
+    map.put("BM", "{\"name\":\"BERMUDA\",\"fmt\":\"%N%n%O%n%A%n%C %Z\"}");
+    map.put("BN", "{\"name\":\"BRUNEI DARUSSALAM\",\"fmt\":\"%N%n%O%n%A%n%C %Z\"}");
+    map.put("BO", "{\"name\":\"BOLIVIA\",\"upper\":\"AC\"}");
+    map.put("BQ", "{\"name\":\"BONAIRE, SINT EUSTATIUS, AND SABA\"}");
+    map.put("BR", "{\"name\":\"BRAZIL\",\"lang\":\"pt\",\"languages\":\"pt\",\"fmt\":\"%O%n%N%n%A%n%D%n%C-%S%n%Z\",\"require\":\"ASCZ\",\"upper\":\"CS\",\"sublocality_name_type\":\"neighborhood\",\"state_name_type\":\"state\",\"width_overrides\":\"%C:L%S:S\"}");
+    map.put("BS", "{\"name\":\"BAHAMAS\",\"lang\":\"en\",\"languages\":\"en\",\"fmt\":\"%N%n%O%n%A%n%C, %S\",\"state_name_type\":\"island\"}");
+    map.put("BT", "{\"name\":\"BHUTAN\"}");
+    map.put("BV", "{\"name\":\"BOUVET ISLAND\"}");
+    map.put("BW", "{\"name\":\"BOTSWANA\"}");
+    map.put("BY", "{\"name\":\"BELARUS\",\"fmt\":\"%S%n%Z %C %X%n%A%n%O%n%N\"}");
+    map.put("BZ", "{\"name\":\"BELIZE\"}");
+    map.put("CA", "{\"name\":\"CANADA\",\"lang\":\"en\",\"languages\":\"en~fr\",\"fmt\":\"%N%n%O%n%A%n%C %S %Z\",\"require\":\"ACSZ\",\"upper\":\"ACNOSZ\"}");
+    map.put("CC", "{\"name\":\"COCOS (KEELING) ISLANDS\",\"fmt\":\"%O%n%N%n%A%n%C %S %Z\",\"upper\":\"CS\"}");
+    map.put("CD", "{\"name\":\"CONGO (DEM. REP.)\",\"fmt\":\"%N%n%O%n%A%n%C %X\"}");
+    map.put("CF", "{\"name\":\"CENTRAL AFRICAN REPUBLIC\"}");
+    map.put("CG", "{\"name\":\"CONGO (REP.)\"}");
+    map.put("CH", "{\"name\":\"SWITZERLAND\",\"lang\":\"de\",\"languages\":\"de~fr~it\",\"fmt\":\"%O%n%N%n%A%nCH-%Z %C\",\"require\":\"ACZ\",\"upper\":\"\",\"postprefix\":\"CH-\"}");
+    map.put("CI", "{\"name\":\"COTE D'IVOIRE\",\"fmt\":\"%N%n%O%n%X %A %C %X\"}");
+    map.put("CK", "{\"name\":\"COOK ISLANDS\"}");
+    map.put("CL", "{\"name\":\"CHILE\",\"lang\":\"es\",\"languages\":\"es\",\"fmt\":\"%N%n%O%n%A%n%Z %C%n%D%n%S\"}");
+    map.put("CM", "{\"name\":\"CAMEROON\"}");
+    map.put("CN", "{\"name\":\"CHINA\",\"lang\":\"zh\",\"languages\":\"zh\",\"lfmt\":\"%N%n%O%n%A%n%D%n%C%n%S, %Z\",\"fmt\":\"%Z%n%S%C%D%n%A%n%O%n%N\",\"require\":\"ACSZ\",\"upper\":\"S\",\"sublocality_name_type\":\"district\",\"width_overrides\":\"%S:S%C:S%D:S\"}");
+    map.put("CO", "{\"name\":\"COLOMBIA\",\"fmt\":\"%N%n%O%n%A%n%C, %S, %Z\",\"require\":\"AS\",\"state_name_type\":\"department\"}");
+    map.put("CR", "{\"name\":\"COSTA RICA\",\"fmt\":\"%N%n%O%n%A%n%Z %C\"}");
+    map.put("CV", "{\"name\":\"CAPE VERDE\",\"lang\":\"pt\",\"languages\":\"pt\",\"fmt\":\"%N%n%O%n%A%n%Z %C%n%S\",\"state_name_type\":\"island\"}");
+    map.put("CW", "{\"name\":\"CURACAO\"}");
+    map.put("CX", "{\"name\":\"CHRISTMAS ISLAND\",\"fmt\":\"%O%n%N%n%A%n%C %S %Z\",\"upper\":\"CS\"}");
+    map.put("CY", "{\"name\":\"CYPRUS\",\"fmt\":\"%N%n%O%n%A%n%Z %C\"}");
+    map.put("CZ", "{\"name\":\"CZECH REP.\",\"fmt\":\"%N%n%O%n%A%n%Z %C\",\"width_overrides\":\"%SN:S%BI:S\"}");
+    map.put("DE", "{\"name\":\"GERMANY\",\"fmt\":\"%N%n%O%n%A%n%Z %C\",\"require\":\"ACZ\"}");
+    map.put("DJ", "{\"name\":\"DJIBOUTI\"}");
+    map.put("DK", "{\"name\":\"DENMARK\",\"fmt\":\"%N%n%O%n%A%n%Z %C\",\"require\":\"ACZ\"}");
+    map.put("DM", "{\"name\":\"DOMINICA\"}");
+    map.put("DO", "{\"name\":\"DOMINICAN REP.\",\"fmt\":\"%N%n%O%n%A%n%Z %C\"}");
+    map.put("DZ", "{\"name\":\"ALGERIA\",\"fmt\":\"%N%n%O%n%A%n%Z %C\"}");
+    map.put("EC", "{\"name\":\"ECUADOR\",\"fmt\":\"%N%n%O%n%A%n%Z%n%C\",\"upper\":\"CZ\"}");
+    map.put("EE", "{\"name\":\"ESTONIA\",\"fmt\":\"%N%n%O%n%A%n%Z %C\"}");
+    map.put("EG", "{\"name\":\"EGYPT\",\"lang\":\"ar\",\"languages\":\"ar\",\"lfmt\":\"%N%n%O%n%A%n%C%n%S%n%Z\",\"fmt\":\"%N%n%O%n%A%n%C%n%S%n%Z\"}");
+    map.put("EH", "{\"name\":\"WESTERN SAHARA\",\"fmt\":\"%N%n%O%n%A%n%Z %C\"}");
+    map.put("ER", "{\"name\":\"ERITREA\"}");
+    map.put("ES", "{\"name\":\"SPAIN\",\"lang\":\"es\",\"languages\":\"es\",\"fmt\":\"%N%n%O%n%A%n%Z %C %S\",\"require\":\"ACSZ\",\"upper\":\"CS\",\"width_overrides\":\"%S:S\"}");
+    map.put("ET", "{\"name\":\"ETHIOPIA\",\"fmt\":\"%N%n%O%n%A%n%Z %C\"}");
+    map.put("FI", "{\"name\":\"FINLAND\",\"fmt\":\"%O%n%N%n%A%nFI-%Z %C\",\"require\":\"ACZ\",\"postprefix\":\"FI-\"}");
+    map.put("FJ", "{\"name\":\"FIJI\"}");
+    map.put("FK", "{\"name\":\"FALKLAND ISLANDS (MALVINAS)\",\"fmt\":\"%N%n%O%n%A%n%X%n%C%n%Z\",\"require\":\"ACZ\",\"upper\":\"CZ\"}");
+    map.put("FM", "{\"name\":\"MICRONESIA (Federated State of)\",\"fmt\":\"%N%n%O%n%A%n%C %S %Z\",\"require\":\"ACSZ\",\"upper\":\"ACNOS\",\"state_name_type\":\"state\",\"zip_name_type\":\"zip\"}");
+    map.put("FO", "{\"name\":\"FAROE ISLANDS\",\"fmt\":\"%N%n%O%n%A%nFO%Z %C\",\"postprefix\":\"FO\"}");
+    map.put("FR", "{\"name\":\"FRANCE\",\"fmt\":\"%O%n%N%n%A%n%Z %C %X\",\"require\":\"ACZ\",\"upper\":\"CX\"}");
+    map.put("GA", "{\"name\":\"GABON\"}");
+    map.put("GB", "{\"name\":\"UNITED KINGDOM\",\"fmt\":\"%N%n%O%n%A%n%C%n%S%n%Z\",\"require\":\"ACZ\",\"upper\":\"CZ\",\"locality_name_type\":\"post_town\",\"state_name_type\":\"county\"}");
+    map.put("GD", "{\"name\":\"GRENADA (WEST INDIES)\"}");
+    map.put("GE", "{\"name\":\"GEORGIA\",\"fmt\":\"%N%n%O%n%A%n%Z %C\"}");
+    map.put("GF", "{\"name\":\"FRENCH GUIANA\",\"fmt\":\"%O%n%N%n%A%n%Z %C %X\",\"require\":\"ACZ\",\"upper\":\"ACX\"}");
+    map.put("GG", "{\"name\":\"CHANNEL ISLANDS\",\"fmt\":\"%N%n%O%n%A%n%X%n%C%nGUERNSEY%n%Z\",\"require\":\"ACZ\",\"upper\":\"CZ\"}");
+    map.put("GH", "{\"name\":\"GHANA\"}");
+    map.put("GI", "{\"name\":\"GIBRALTAR\",\"fmt\":\"%N%n%O%n%A%nGIBRALTAR%n%Z\",\"require\":\"A\"}");
+    map.put("GL", "{\"name\":\"GREENLAND\",\"fmt\":\"%N%n%O%n%A%n%Z %C\",\"require\":\"ACZ\"}");
+    map.put("GM", "{\"name\":\"GAMBIA\"}");
+    map.put("GN", "{\"name\":\"GUINEA\",\"fmt\":\"%N%n%O%n%Z %A %C\"}");
+    map.put("GP", "{\"name\":\"GUADELOUPE\",\"fmt\":\"%O%n%N%n%A%n%Z %C %X\",\"require\":\"ACZ\",\"upper\":\"ACX\"}");
+    map.put("GQ", "{\"name\":\"EQUATORIAL GUINEA\"}");
+    map.put("GR", "{\"name\":\"GREECE\",\"fmt\":\"%N%n%O%n%A%n%Z %C\",\"require\":\"ACZ\"}");
+    map.put("GS", "{\"name\":\"SOUTH GEORGIA\",\"fmt\":\"%N%n%O%n%A%n%X%n%C%n%Z\",\"require\":\"ACZ\",\"upper\":\"CZ\"}");
+    map.put("GT", "{\"name\":\"GUATEMALA\",\"fmt\":\"%N%n%O%n%A%n%Z- %C\"}");
+    map.put("GU", "{\"name\":\"GUAM\",\"fmt\":\"%N%n%O%n%A%n%C %S %Z\",\"require\":\"ACSZ\",\"upper\":\"ACNOS\",\"state_name_type\":\"state\",\"zip_name_type\":\"zip\"}");
+    map.put("GW", "{\"name\":\"GUINEA-BISSAU\",\"fmt\":\"%N%n%O%n%A%n%Z %C\"}");
+    map.put("GY", "{\"name\":\"GUYANA\"}");
+    map.put("HK", "{\"name\":\"HONG KONG\",\"lang\":\"zh-Hant\",\"languages\":\"zh-Hant~en\",\"lfmt\":\"%N%n%O%n%A%n%C%n%S\",\"fmt\":\"%S%n%C%n%A%n%O%n%N\",\"require\":\"AS\",\"upper\":\"S\",\"locality_name_type\":\"district\",\"state_name_type\":\"area\",\"width_overrides\":\"%S:S%C:L\"}");
+    map.put("HM", "{\"name\":\"HEARD AND MCDONALD ISLANDS\",\"fmt\":\"%O%n%N%n%A%n%C %S %Z\",\"upper\":\"CS\"}");
+    map.put("HN", "{\"name\":\"HONDURAS\",\"fmt\":\"%N%n%O%n%A%n%C, %S%n%Z\",\"require\":\"ACS\"}");
+    map.put("HR", "{\"name\":\"CROATIA\",\"fmt\":\"%N%n%O%n%A%nHR-%Z %C\",\"postprefix\":\"HR-\"}");
+    map.put("HT", "{\"name\":\"HAITI\",\"fmt\":\"%N%n%O%n%A%nHT%Z %C %X\",\"postprefix\":\"HT\"}");
+    map.put("HU", "{\"name\":\"HUNGARY (Rep.)\",\"fmt\":\"%N%n%O%n%C%n%A%n%Z\",\"require\":\"ACS\",\"upper\":\"ACNO\"}");
+    map.put("ID", "{\"name\":\"INDONESIA\",\"lang\":\"id\",\"languages\":\"id\",\"fmt\":\"%N%n%O%n%A%n%C%n%S %Z\",\"require\":\"AS\",\"width_overrides\":\"%BI:S%NH:N\"}");
+    map.put("IE", "{\"name\":\"IRELAND\",\"lang\":\"en\",\"languages\":\"en\",\"fmt\":\"%N%n%O%n%A%n%C%n%S\",\"state_name_type\":\"county\"}");
+    map.put("IL", "{\"name\":\"ISRAEL\",\"fmt\":\"%N%n%O%n%A%n%C %Z\"}");
+    map.put("IM", "{\"name\":\"ISLE OF MAN\",\"fmt\":\"%N%n%O%n%A%n%X%n%C%n%Z\",\"require\":\"ACZ\",\"upper\":\"CZ\"}");
+    map.put("IN", "{\"name\":\"INDIA\",\"lang\":\"en\",\"languages\":\"en\",\"fmt\":\"%N%n%O%n%A%n%C %Z%n%S\",\"require\":\"ACSZ\",\"state_name_type\":\"state\",\"zip_name_type\":\"pin\",\"width_overrides\":\"%NH:L\"}");
+    map.put("IO", "{\"name\":\"BRITISH INDIAN OCEAN TERRITORY\",\"fmt\":\"%N%n%O%n%A%n%X%n%C%n%Z\",\"require\":\"ACZ\",\"upper\":\"CZ\"}");
+    map.put("IQ", "{\"name\":\"IRAQ\",\"fmt\":\"%O%n%N%n%A%n%C, %S%n%Z\",\"require\":\"ACS\",\"upper\":\"CS\"}");
+    map.put("IR", "{\"name\":\"IRAN\",\"fmt\":\"%O%n%N%n%S%n%C, %D%n%A%n%Z\",\"sublocality_name_type\":\"neighborhood\"}");
+    map.put("IS", "{\"name\":\"ICELAND\",\"fmt\":\"%N%n%O%n%A%n%Z %C\"}");
+    map.put("IT", "{\"name\":\"ITALY\",\"lang\":\"it\",\"languages\":\"it\",\"fmt\":\"%N%n%O%n%A%n%Z %C %S\",\"require\":\"ACSZ\",\"upper\":\"CS\",\"width_overrides\":\"%S:S\"}");
+    map.put("JE", "{\"name\":\"CHANNEL ISLANDS\",\"fmt\":\"%N%n%O%n%A%n%X%n%C%nJERSEY%n%Z\",\"require\":\"ACZ\",\"upper\":\"CZ\"}");
+    map.put("JM", "{\"name\":\"JAMAICA\",\"lang\":\"en\",\"languages\":\"en\",\"fmt\":\"%N%n%O%n%A%n%C%n%S %X\",\"require\":\"ACS\",\"state_name_type\":\"parish\"}");
+    map.put("JO", "{\"name\":\"JORDAN\",\"fmt\":\"%N%n%O%n%A%n%C %Z\"}");
+    map.put("JP", "{\"name\":\"JAPAN\",\"lang\":\"ja\",\"languages\":\"ja\",\"lfmt\":\"%N%n%O%n%A%n%C, %S%n%Z\",\"fmt\":\"〒%Z%n%S%C%n%A%n%O%n%N\",\"require\":\"ACSZ\",\"upper\":\"S\",\"state_name_type\":\"prefecture\",\"width_overrides\":\"%S:S\"}");
+    map.put("KE", "{\"name\":\"KENYA\",\"fmt\":\"%N%n%O%n%A%n%C%n%Z\"}");
+    map.put("KG", "{\"name\":\"KYRGYZSTAN\",\"fmt\":\"%Z %C %X%n%A%n%O%n%N\"}");
+    map.put("KH", "{\"name\":\"CAMBODIA\",\"fmt\":\"%N%n%O%n%A%n%C %Z\"}");
+    map.put("KI", "{\"name\":\"KIRIBATI\",\"fmt\":\"%N%n%O%n%A%n%S%n%C\",\"upper\":\"ACNOS\",\"state_name_type\":\"island\"}");
+    map.put("KM", "{\"name\":\"COMOROS\",\"upper\":\"AC\"}");
+    map.put("KN", "{\"name\":\"SAINT KITTS AND NEVIS\",\"lang\":\"en\",\"languages\":\"en\",\"fmt\":\"%N%n%O%n%A%n%C, %S\",\"require\":\"ACS\",\"state_name_type\":\"island\"}");
+    map.put("KR", "{\"name\":\"SOUTH KOREA\",\"lang\":\"ko\",\"languages\":\"ko\",\"lfmt\":\"%N%n%O%n%A%n%D%n%C%n%S%n%Z\",\"fmt\":\"%S %C%D%n%A%n%O%n%N%n%Z\",\"require\":\"ACSZ\",\"upper\":\"Z\",\"sublocality_name_type\":\"district\",\"state_name_type\":\"do_si\"}");
+    map.put("KW", "{\"name\":\"KUWAIT\",\"fmt\":\"%N%n%O%n%A%n%Z %C\"}");
+    map.put("KY", "{\"name\":\"CAYMAN ISLANDS\",\"lang\":\"en\",\"languages\":\"en\",\"fmt\":\"%N%n%O%n%A%n%S %Z\",\"require\":\"AS\",\"state_name_type\":\"island\"}");
+    map.put("KZ", "{\"name\":\"KAZAKHSTAN\",\"fmt\":\"%Z%n%S%n%C%n%A%n%O%n%N\"}");
+    map.put("LA", "{\"name\":\"LAO (PEOPLE'S DEM. REP.)\",\"fmt\":\"%N%n%O%n%A%n%Z %C\"}");
+    map.put("LB", "{\"name\":\"LEBANON\",\"fmt\":\"%N%n%O%n%A%n%C %Z\"}");
+    map.put("LC", "{\"name\":\"SAINT LUCIA\"}");
+    map.put("LI", "{\"name\":\"LIECHTENSTEIN\",\"fmt\":\"%O%n%N%n%A%nFL-%Z %C\",\"require\":\"ACZ\",\"postprefix\":\"FL-\"}");
+    map.put("LK", "{\"name\":\"SRI LANKA\",\"fmt\":\"%N%n%O%n%A%n%C%n%Z\"}");
+    map.put("LR", "{\"name\":\"LIBERIA\",\"fmt\":\"%N%n%O%n%A%n%Z %C %X\"}");
+    map.put("LS", "{\"name\":\"LESOTHO\",\"fmt\":\"%N%n%O%n%A%n%C %Z\"}");
+    map.put("LT", "{\"name\":\"LITHUANIA\",\"fmt\":\"%O%n%N%n%A%nLT-%Z %C\",\"postprefix\":\"LT-\"}");
+    map.put("LU", "{\"name\":\"LUXEMBOURG\",\"fmt\":\"%O%n%N%n%A%nL-%Z %C\",\"require\":\"ACZ\",\"postprefix\":\"L-\"}");
+    map.put("LV", "{\"name\":\"LATVIA\",\"fmt\":\"%N%n%O%n%A%n%C, %Z\"}");
+    map.put("LY", "{\"name\":\"LIBYA\"}");
+    map.put("MA", "{\"name\":\"MOROCCO\",\"fmt\":\"%N%n%O%n%A%n%Z %C\"}");
+    map.put("MC", "{\"name\":\"MONACO\",\"fmt\":\"%N%n%O%n%A%nMC-%Z %C %X\",\"postprefix\":\"MC-\"}");
+    map.put("MD", "{\"name\":\"Rep. MOLDOVA\",\"fmt\":\"%N%n%O%n%A%nMD-%Z %C\",\"postprefix\":\"MD-\"}");
+    map.put("ME", "{\"name\":\"MONTENEGRO\",\"fmt\":\"%N%n%O%n%A%n%Z %C\"}");
+    map.put("MF", "{\"name\":\"SAINT MARTIN\",\"fmt\":\"%O%n%N%n%A%n%Z %C %X\",\"require\":\"ACZ\",\"upper\":\"ACX\"}");
+    map.put("MG", "{\"name\":\"MADAGASCAR\",\"fmt\":\"%N%n%O%n%A%n%Z %C\"}");
+    map.put("MH", "{\"name\":\"MARSHALL ISLANDS\",\"fmt\":\"%N%n%O%n%A%n%C %S %Z\",\"require\":\"ACSZ\",\"upper\":\"ACNOS\",\"state_name_type\":\"state\",\"zip_name_type\":\"zip\"}");
+    map.put("MK", "{\"name\":\"MACEDONIA\",\"fmt\":\"%N%n%O%n%A%n%Z %C\"}");
+    map.put("ML", "{\"name\":\"MALI\"}");
+    map.put("MM", "{\"name\":\"MYANMAR\",\"fmt\":\"%N%n%O%n%A%n%C, %Z\"}");
+    map.put("MN", "{\"name\":\"MONGOLIA\",\"fmt\":\"%N%n%O%n%A%n%S %C-%X%n%Z\"}");
+    map.put("MO", "{\"name\":\"MACAO\",\"lfmt\":\"%N%n%O%n%A\",\"fmt\":\"%A%n%O%n%N\",\"require\":\"A\"}");
+    map.put("MP", "{\"name\":\"NORTHERN MARIANA ISLANDS\",\"fmt\":\"%N%n%O%n%A%n%C %S %Z\",\"require\":\"ACSZ\",\"upper\":\"ACNOS\",\"state_name_type\":\"state\",\"zip_name_type\":\"zip\"}");
+    map.put("MQ", "{\"name\":\"MARTINIQUE\",\"fmt\":\"%O%n%N%n%A%n%Z %C %X\",\"require\":\"ACZ\",\"upper\":\"ACX\"}");
+    map.put("MR", "{\"name\":\"MAURITANIA\",\"upper\":\"AC\"}");
+    map.put("MS", "{\"name\":\"MONTSERRAT\"}");
+    map.put("MT", "{\"name\":\"MALTA\",\"fmt\":\"%N%n%O%n%A%n%C %Z\",\"upper\":\"CZ\"}");
+    map.put("MU", "{\"name\":\"MAURITIUS\",\"fmt\":\"%N%n%O%n%A%n%Z%n%C\",\"upper\":\"CZ\"}");
+    map.put("MV", "{\"name\":\"MALDIVES\",\"fmt\":\"%N%n%O%n%A%n%C %Z\"}");
+    map.put("MW", "{\"name\":\"MALAWI\",\"fmt\":\"%N%n%O%n%A%n%C %X\"}");
+    map.put("MX", "{\"name\":\"MEXICO\",\"lang\":\"es\",\"languages\":\"es\",\"fmt\":\"%N%n%O%n%A%n%D%n%Z %C, %S\",\"require\":\"ACZ\",\"upper\":\"CSZ\",\"sublocality_name_type\":\"neighborhood\",\"state_name_type\":\"state\",\"width_overrides\":\"%S:S%S2:N%S3:N%LP:N\"}");
+    map.put("MY", "{\"name\":\"MALAYSIA\",\"lang\":\"ms\",\"languages\":\"ms\",\"fmt\":\"%N%n%O%n%A%n%D%n%Z %C%n%S\",\"require\":\"ACZ\",\"upper\":\"CS\",\"sublocality_name_type\":\"village_township\",\"state_name_type\":\"state\"}");
+    map.put("MZ", "{\"name\":\"MOZAMBIQUE\"}");
+    map.put("NA", "{\"name\":\"NAMIBIA\"}");
+    map.put("NC", "{\"name\":\"NEW CALEDONIA\",\"fmt\":\"%O%n%N%n%A%n%Z %C %X\",\"require\":\"ACZ\",\"upper\":\"ACX\"}");
+    map.put("NE", "{\"name\":\"NIGER\",\"fmt\":\"%N%n%O%n%A%n%Z %C\"}");
+    map.put("NF", "{\"name\":\"NORFOLK ISLAND\",\"fmt\":\"%O%n%N%n%A%n%C %S %Z\",\"upper\":\"CS\"}");
+    map.put("NG", "{\"name\":\"NIGERIA\",\"lang\":\"en\",\"languages\":\"en\",\"fmt\":\"%N%n%O%n%A%n%C %Z%n%S\",\"upper\":\"CS\",\"state_name_type\":\"state\"}");
+    map.put("NI", "{\"name\":\"NICARAGUA\",\"lang\":\"es\",\"languages\":\"es\",\"fmt\":\"%N%n%O%n%A%n%Z%n%C, %S\",\"upper\":\"CS\",\"state_name_type\":\"department\"}");
+    map.put("NL", "{\"name\":\"NETHERLANDS\",\"fmt\":\"%O%n%N%n%A%n%Z %C\",\"require\":\"ACZ\"}");
+    map.put("NO", "{\"name\":\"NORWAY\",\"fmt\":\"%N%n%O%n%A%n%Z %C\",\"require\":\"ACZ\"}");
+    map.put("NP", "{\"name\":\"NEPAL\",\"fmt\":\"%N%n%O%n%A%n%C %Z\"}");
+    map.put("NR", "{\"name\":\"NAURU CENTRAL PACIFIC\",\"lang\":\"en\",\"languages\":\"en\",\"fmt\":\"%N%n%O%n%A%n%S\",\"require\":\"AS\",\"state_name_type\":\"district\"}");
+    map.put("NU", "{\"name\":\"NIUE\"}");
+    map.put("NZ", "{\"name\":\"NEW ZEALAND\",\"fmt\":\"%N%n%O%n%A%n%D%n%C %Z\",\"require\":\"ACZ\"}");
+    map.put("OM", "{\"name\":\"OMAN\",\"fmt\":\"%N%n%O%n%A%n%Z%n%C\"}");
+    map.put("PA", "{\"name\":\"PANAMA (REP.)\",\"fmt\":\"%N%n%O%n%A%n%C%n%S\",\"upper\":\"CS\"}");
+    map.put("PE", "{\"name\":\"PERU\"}");
+    map.put("PF", "{\"name\":\"FRENCH POLYNESIA\",\"fmt\":\"%N%n%O%n%A%n%Z %C %S\",\"require\":\"ACSZ\",\"upper\":\"CS\",\"state_name_type\":\"island\"}");
+    map.put("PG", "{\"name\":\"PAPUA NEW GUINEA\",\"fmt\":\"%N%n%O%n%A%n%C %Z %S\",\"require\":\"ACS\"}");
+    map.put("PH", "{\"name\":\"PHILIPPINES\",\"lang\":\"en\",\"languages\":\"en\",\"fmt\":\"%N%n%O%n%A%n%D, %C%n%Z %S\"}");
+    map.put("PK", "{\"name\":\"PAKISTAN\",\"fmt\":\"%N%n%O%n%A%n%C-%Z\"}");
+    map.put("PL", "{\"name\":\"POLAND\",\"fmt\":\"%N%n%O%n%A%n%Z %C\",\"require\":\"ACZ\"}");
+    map.put("PM", "{\"name\":\"ST. PIERRE AND MIQUELON\",\"fmt\":\"%O%n%N%n%A%n%Z %C %X\",\"require\":\"ACZ\",\"upper\":\"ACX\"}");
+    map.put("PN", "{\"name\":\"PITCAIRN\",\"fmt\":\"%N%n%O%n%A%n%X%n%C%n%Z\",\"require\":\"ACZ\",\"upper\":\"CZ\"}");
+    map.put("PR", "{\"name\":\"PUERTO RICO\",\"fmt\":\"%N%n%O%n%A%n%C PR %Z\",\"require\":\"ACZ\",\"upper\":\"ACNO\",\"zip_name_type\":\"zip\",\"postprefix\":\"PR\"}");
+    map.put("PS", "{\"name\":\"PALESTINIAN TERRITORY\"}");
+    map.put("PT", "{\"name\":\"PORTUGAL\",\"fmt\":\"%N%n%O%n%A%n%Z %C\",\"require\":\"ACZ\"}");
+    map.put("PW", "{\"name\":\"PALAU\",\"fmt\":\"%N%n%O%n%A%n%C %S %Z\",\"require\":\"ACSZ\",\"upper\":\"ACNOS\",\"state_name_type\":\"state\",\"zip_name_type\":\"zip\"}");
+    map.put("PY", "{\"name\":\"PARAGUAY\",\"fmt\":\"%N%n%O%n%A%n%Z %C\"}");
+    map.put("QA", "{\"name\":\"QATAR\",\"upper\":\"AC\"}");
+    map.put("RE", "{\"name\":\"REUNION\",\"fmt\":\"%O%n%N%n%A%n%Z %C %X\",\"require\":\"ACZ\",\"upper\":\"ACX\"}");
+    map.put("RO", "{\"name\":\"ROMANIA\",\"fmt\":\"%N%n%O%n%A%n%Z %C\",\"upper\":\"AC\"}");
+    map.put("RS", "{\"name\":\"REPUBLIC OF SERBIA\",\"fmt\":\"%N%n%O%n%A%n%Z %C\"}");
+    map.put("RU", "{\"name\":\"RUSSIAN FEDERATION\",\"lang\":\"ru\",\"languages\":\"ru\",\"lfmt\":\"%N%n%O%n%A%n%C%n%S%n%Z\",\"fmt\":\"%N%n%O%n%A%n%C%n%S%n%Z\",\"require\":\"ACZ\",\"upper\":\"AC\",\"state_name_type\":\"oblast\"}");
+    map.put("RW", "{\"name\":\"RWANDA\",\"upper\":\"AC\"}");
+    map.put("SA", "{\"name\":\"SAUDI ARABIA\",\"fmt\":\"%N%n%O%n%A%n%C %Z\"}");
+    map.put("SB", "{\"name\":\"SOLOMON ISLANDS\"}");
+    map.put("SC", "{\"name\":\"SEYCHELLES\",\"fmt\":\"%N%n%O%n%A%n%C%n%S\",\"upper\":\"S\",\"state_name_type\":\"island\"}");
+    map.put("SE", "{\"name\":\"SWEDEN\",\"fmt\":\"%O%n%N%n%A%nSE-%Z %C\",\"require\":\"ACZ\",\"postprefix\":\"SE-\"}");
+    map.put("SG", "{\"name\":\"REP. OF SINGAPORE\",\"fmt\":\"%N%n%O%n%A%nSINGAPORE %Z\",\"require\":\"AZ\"}");
+    map.put("SH", "{\"name\":\"SAINT HELENA\",\"fmt\":\"%N%n%O%n%A%n%X%n%C%n%Z\",\"require\":\"ACZ\",\"upper\":\"CZ\"}");
+    map.put("SI", "{\"name\":\"SLOVENIA\",\"fmt\":\"%N%n%O%n%A%nSI- %Z %C\",\"postprefix\":\"SI-\"}");
+    map.put("SJ", "{\"name\":\"SVALBARD AND JAN MAYEN ISLANDS\",\"fmt\":\"%N%n%O%n%A%n%Z %C\",\"require\":\"ACZ\"}");
+    map.put("SK", "{\"name\":\"SLOVAKIA\",\"fmt\":\"%N%n%O%n%A%n%Z %C\",\"width_overrides\":\"%SN:S%BI:S\"}");
+    map.put("SL", "{\"name\":\"SIERRA LEONE\"}");
+    map.put("SM", "{\"name\":\"SAN MARINO\",\"fmt\":\"%N%n%O%n%A%n%Z %C\",\"require\":\"AZ\"}");
+    map.put("SN", "{\"name\":\"SENEGAL\",\"fmt\":\"%N%n%O%n%A%n%Z %C\"}");
+    map.put("SO", "{\"name\":\"SOMALIA\",\"lang\":\"so\",\"languages\":\"so\",\"fmt\":\"%N%n%O%n%A%n%C, %S %Z\",\"require\":\"ACS\",\"upper\":\"ACS\"}");
+    map.put("SR", "{\"name\":\"SURINAME\",\"lang\":\"nl\",\"languages\":\"nl\",\"fmt\":\"%N%n%O%n%A%n%C %X%n%S\",\"upper\":\"AS\"}");
+    map.put("SS", "{\"name\":\"SOUTH SUDAN\"}");
+    map.put("ST", "{\"name\":\"SAO TOME AND PRINCIPE\",\"fmt\":\"%N%n%O%n%A%n%C %X\"}");
+    map.put("SV", "{\"name\":\"EL SALVADOR\",\"lang\":\"es\",\"languages\":\"es\",\"fmt\":\"%N%n%O%n%A%n%Z-%C%n%S\",\"require\":\"ACS\",\"upper\":\"CSZ\"}");
+    map.put("SX", "{\"name\":\"SINT MAARTEN\"}");
+    map.put("SZ", "{\"name\":\"SWAZILAND\",\"fmt\":\"%N%n%O%n%A%n%C%n%Z\",\"upper\":\"ACZ\"}");
+    map.put("TA", "{\"name\":\"TRISTAN DA CUNHA\"}");
+    map.put("TC", "{\"name\":\"TURKS AND CAICOS ISLANDS\",\"fmt\":\"%N%n%O%n%A%n%X%n%C%n%Z\",\"require\":\"ACZ\",\"upper\":\"CZ\"}");
+    map.put("TD", "{\"name\":\"CHAD\"}");
+    map.put("TF", "{\"name\":\"FRENCH SOUTHERN TERRITORIES\"}");
+    map.put("TG", "{\"name\":\"TOGO\"}");
+    map.put("TH", "{\"name\":\"THAILAND\",\"lang\":\"th\",\"languages\":\"th\",\"lfmt\":\"%N%n%O%n%A%n%D, %C%n%S %Z\",\"fmt\":\"%N%n%O%n%A%n%D %C%n%S %Z\",\"upper\":\"S\"}");
+    map.put("TJ", "{\"name\":\"TAJIKISTAN\",\"fmt\":\"%N%n%O%n%A%n%Z %C\"}");
+    map.put("TK", "{\"name\":\"TOKELAU\"}");
+    map.put("TL", "{\"name\":\"TIMOR-LESTE\"}");
+    map.put("TM", "{\"name\":\"TURKMENISTAN\",\"fmt\":\"%N%n%O%n%A%n%Z %C\"}");
+    map.put("TN", "{\"name\":\"TUNISIA\",\"fmt\":\"%N%n%O%n%A%n%Z %C\"}");
+    map.put("TO", "{\"name\":\"TONGA\"}");
+    map.put("TR", "{\"name\":\"TURKEY\",\"lang\":\"tr\",\"languages\":\"tr\",\"fmt\":\"%N%n%O%n%A%n%Z %C/%S\",\"require\":\"ACZ\",\"locality_name_type\":\"district\"}");
+    map.put("TT", "{\"name\":\"TRINIDAD AND TOBAGO\"}");
+    map.put("TV", "{\"name\":\"TUVALU\",\"lang\":\"tyv\",\"languages\":\"tyv\",\"fmt\":\"%N%n%O%n%A%n%X%n%C%n%S\",\"upper\":\"ACS\",\"state_name_type\":\"island\"}");
+    map.put("TW", "{\"name\":\"TAIWAN\",\"lang\":\"zh-Hant\",\"languages\":\"zh-Hant\",\"lfmt\":\"%N%n%O%n%A%n%C, %S %Z\",\"fmt\":\"%Z%n%S%C%n%A%n%O%n%N\",\"require\":\"ACSZ\",\"state_name_type\":\"county\"}");
+    map.put("TZ", "{\"name\":\"TANZANIA (UNITED REP.)\",\"fmt\":\"%N%n%O%n%A%n%Z %C\"}");
+    map.put("UA", "{\"name\":\"UKRAINE\",\"lang\":\"uk\",\"languages\":\"uk\",\"lfmt\":\"%N%n%O%n%A%n%C%n%S%n%Z\",\"fmt\":\"%N%n%O%n%A%n%C%n%S%n%Z\",\"require\":\"ACZ\",\"state_name_type\":\"oblast\"}");
+    map.put("UG", "{\"name\":\"UGANDA\"}");
+    map.put("UM", "{\"name\":\"UNITED STATES MINOR OUTLYING ISLANDS\",\"fmt\":\"%N%n%O%n%A%n%C %S %Z\",\"require\":\"ACS\",\"upper\":\"ACNOS\",\"state_name_type\":\"state\",\"zip_name_type\":\"zip\"}");
+    map.put("US", "{\"name\":\"UNITED STATES\",\"lang\":\"en\",\"languages\":\"en\",\"fmt\":\"%N%n%O%n%A%n%C, %S %Z\",\"require\":\"ACSZ\",\"upper\":\"CS\",\"state_name_type\":\"state\",\"zip_name_type\":\"zip\",\"width_overrides\":\"%S:S\"}");
+    map.put("UY", "{\"name\":\"URUGUAY\",\"lang\":\"es\",\"languages\":\"es\",\"fmt\":\"%N%n%O%n%A%n%Z %C %S\",\"upper\":\"CS\"}");
+    map.put("UZ", "{\"name\":\"UZBEKISTAN\",\"fmt\":\"%N%n%O%n%A%n%Z %C%n%S\",\"upper\":\"CS\"}");
+    map.put("VA", "{\"name\":\"VATICAN\",\"fmt\":\"%N%n%O%n%A%n%Z %C\"}");
+    map.put("VC", "{\"name\":\"SAINT VINCENT AND THE GRENADINES (ANTILLES)\"}");
+    map.put("VE", "{\"name\":\"VENEZUELA\",\"lang\":\"es\",\"languages\":\"es\",\"fmt\":\"%N%n%O%n%A%n%C %Z, %S\",\"require\":\"ACS\",\"upper\":\"CS\"}");
+    map.put("VG", "{\"name\":\"VIRGIN ISLANDS (BRITISH)\",\"fmt\":\"%N%n%O%n%A%n%C%n%Z\",\"require\":\"A\"}");
+    map.put("VI", "{\"name\":\"VIRGIN ISLANDS (U.S.)\",\"fmt\":\"%N%n%O%n%A%n%C %S %Z\",\"require\":\"ACSZ\",\"upper\":\"ACNOS\",\"state_name_type\":\"state\",\"zip_name_type\":\"zip\"}");
+    map.put("VN", "{\"name\":\"VIET NAM\",\"lang\":\"vi\",\"languages\":\"vi\",\"lfmt\":\"%N%n%O%n%A%n%C%n%S %Z\",\"fmt\":\"%N%n%O%n%A%n%C%n%S %Z\"}");
+    map.put("VU", "{\"name\":\"VANUATU\"}");
+    map.put("WF", "{\"name\":\"WALLIS AND FUTUNA ISLANDS\",\"fmt\":\"%O%n%N%n%A%n%Z %C %X\",\"require\":\"ACZ\",\"upper\":\"ACX\"}");
+    map.put("WS", "{\"name\":\"SAMOA\"}");
+    map.put("XK", "{\"name\":\"KOSOVO\",\"fmt\":\"%N%n%O%n%A%n%Z %C\"}");
+    map.put("YE", "{\"name\":\"YEMEN\"}");
+    map.put("YT", "{\"name\":\"MAYOTTE\",\"fmt\":\"%O%n%N%n%A%n%Z %C %X\",\"require\":\"ACZ\",\"upper\":\"ACX\"}");
+    map.put("ZA", "{\"name\":\"SOUTH AFRICA\",\"fmt\":\"%N%n%O%n%A%n%D%n%C%n%Z\",\"require\":\"ACZ\"}");
+    map.put("ZM", "{\"name\":\"ZAMBIA\",\"fmt\":\"%N%n%O%n%A%n%Z %C\"}");
+    map.put("ZW", "{\"name\":\"ZIMBABWE\"}");
+    map.put("ZZ", "{\"fmt\":\"%N%n%O%n%A%n%C\",\"require\":\"AC\",\"upper\":\"C\",\"sublocality_name_type\":\"suburb\",\"locality_name_type\":\"city\",\"state_name_type\":\"province\",\"zip_name_type\":\"postal\"}");
+    return Collections.unmodifiableMap(map);
   }
 }
diff --git a/common/src/test/java/com/google/i18n/addressinput/common/AddressFieldTest.java b/common/src/test/java/com/google/i18n/addressinput/common/AddressFieldTest.java
index 12a49da..a780244 100644
--- a/common/src/test/java/com/google/i18n/addressinput/common/AddressFieldTest.java
+++ b/common/src/test/java/com/google/i18n/addressinput/common/AddressFieldTest.java
@@ -18,6 +18,8 @@
 
 import static org.junit.Assert.assertEquals;
 
+import com.google.i18n.addressinput.common.AddressField.WidthType;
+
 import org.junit.Test;
 import org.junit.runner.RunWith;
 import org.junit.runners.JUnit4;
@@ -31,4 +33,23 @@
   @Test public void testGetChar() throws Exception {
     assertEquals('R', AddressField.COUNTRY.getChar());
   }
+
+  @Test public void testGetWidthTypeForPostalCode() throws Exception {
+    // Postal (& sorting) code always have SHORT width.
+    assertEquals(WidthType.SHORT, AddressField.POSTAL_CODE.getWidthTypeForRegion("US"));
+    assertEquals(WidthType.SHORT, AddressField.SORTING_CODE.getWidthTypeForRegion("DE"));
+  }
+
+  @Test public void testGetWidthTypeForCountry() throws Exception {
+    // No overrides for country, so we use the default, LONG.
+    assertEquals(WidthType.LONG, AddressField.COUNTRY.getWidthTypeForRegion("US"));
+    assertEquals(WidthType.LONG, AddressField.COUNTRY.getWidthTypeForRegion("CH"));
+  }
+
+  @Test public void testGetWidthTypeWithOverride() throws Exception {
+    // With an override.
+    assertEquals(WidthType.SHORT, AddressField.LOCALITY.getWidthTypeForRegion("CN"));
+    // Without an override.
+    assertEquals(WidthType.LONG, AddressField.LOCALITY.getWidthTypeForRegion("US"));
+  }
 }
diff --git a/common/src/test/java/com/google/i18n/addressinput/common/FormatInterpreterTest.java b/common/src/test/java/com/google/i18n/addressinput/common/FormatInterpreterTest.java
index f58d6ec..4e2091e 100644
--- a/common/src/test/java/com/google/i18n/addressinput/common/FormatInterpreterTest.java
+++ b/common/src/test/java/com/google/i18n/addressinput/common/FormatInterpreterTest.java
@@ -17,6 +17,7 @@
 package com.google.i18n.addressinput.common;
 
 import static com.google.common.truth.Truth.assertThat;
+import com.google.i18n.addressinput.common.AddressField.WidthType;
 import static java.util.Arrays.asList;
 
 import com.google.i18n.addressinput.common.LookupKey.ScriptType;
@@ -25,6 +26,9 @@
 import org.junit.runner.RunWith;
 import org.junit.runners.JUnit4;
 
+import java.util.HashMap;
+import java.util.Map;
+
 @RunWith(JUnit4.class)
 public class FormatInterpreterTest {
 
@@ -174,4 +178,54 @@
     assertThat(formatInterpreter.getEnvelopeAddress(svAddressWithPostCode))
         .containsExactly("Some Street 12", "CP 2101-Ahuachapán", "Ahuachapán").inOrder();
   }
+
+  private Map<String, String> createWidthOverrideRegionData(String overridesString) {
+    Map<String, String> map = new HashMap<String, String>(1);
+    map.put("US", "{\"width_overrides\":\"" + overridesString + "\"}");
+    return map;
+  }
+
+  @Test public void testGetWidthOverride_goodData() {
+    Map<String, String> fakeData = createWidthOverrideRegionData("%S:L%C:S");
+    assertThat(FormatInterpreter.getWidthOverride(AddressField.LOCALITY, "US", fakeData))
+        .isEqualTo(WidthType.SHORT);
+    assertThat(FormatInterpreter.getWidthOverride(AddressField.ADMIN_AREA, "US", fakeData))
+        .isEqualTo(WidthType.LONG);
+    assertThat(FormatInterpreter.getWidthOverride(AddressField.POSTAL_CODE, "US", fakeData))
+        .isNull();
+  }
+
+  @Test public void testGetWidthOverride_singleOverride() {
+    Map<String, String> fakeData = createWidthOverrideRegionData("%S:S");
+    assertThat(FormatInterpreter.getWidthOverride(AddressField.ADMIN_AREA, "US", fakeData))
+        .isEqualTo(WidthType.SHORT);
+    assertThat(FormatInterpreter.getWidthOverride(AddressField.LOCALITY, "US", fakeData)).isNull();
+  }
+
+  @Test public void testGetWidthOverride_badData() {
+    // Doesn't test that the parsing code actually just skips bad keys/values. That's nice, but
+    // not essential.
+    for (String overridesString : new String[]{
+        "", "%", ":", "%%", "%:", "%CX", "%CX:", "C:S", "%C:", "%C:SS", "%C:SS%Q:L"}) {
+      Map<String, String> fakeData = createWidthOverrideRegionData(overridesString);
+      for (AddressField field : AddressField.values()) {
+        assertThat(FormatInterpreter.getWidthOverride(field, "US", fakeData))
+            .named("With field " + field + " and overrides string '" + overridesString + "'")
+            .isNull();
+      }
+    }
+  }
+
+  @Test public void testGetWidthOverride_skipTooLongKeys() {
+    for (String overridesString : new String[]{
+        "%NH:L%C:S", "%Z:L%BG:S%C:S", "%C:S%NH:S", "%NH:QL%C:S", "%NH:L%C:S%BG:L"}) {
+      Map<String, String> fakeData = createWidthOverrideRegionData(overridesString);
+        assertThat(FormatInterpreter.getWidthOverride(AddressField.LOCALITY, "US", fakeData))
+            .named("For LOCALITY (C) and overrides string '" + overridesString + "'")
+            .isEqualTo(WidthType.SHORT);
+        assertThat(FormatInterpreter.getWidthOverride(AddressField.ADMIN_AREA, "US", fakeData))
+            .named("For ADMIN_AREA (S) and overrides string '" + overridesString + "'")
+            .isNull();
+    }
+  }
 }
diff --git a/common/src/test/java/com/google/i18n/addressinput/common/RegionDataConstantsTest.java b/common/src/test/java/com/google/i18n/addressinput/common/RegionDataConstantsTest.java
index 3231354..ba73653 100644
--- a/common/src/test/java/com/google/i18n/addressinput/common/RegionDataConstantsTest.java
+++ b/common/src/test/java/com/google/i18n/addressinput/common/RegionDataConstantsTest.java
@@ -39,14 +39,4 @@
     assertNotNull("Data for 'ZZ' is missing (needed for default region info.)",
         RegionDataConstants.getCountryFormatMap().get("ZZ"));
   }
-
-  @Test public void testStringsAreConvertedIntoJson() throws Exception {
-    String[] input = {"key", "value", "key2", "value2"};
-    // Input order is not maintained, since we build this using JSON objects. This is
-    // unimportant, so long as the key-value mappings are maintained.
-    String expectedOutput1 = "{\"key\":\"value\",\"key2\":\"value2\"}";
-    String expectedOutput2 = "{\"key2\":\"value2\",\"key\":\"value\"}";
-    String actualOutput = RegionDataConstants.convertArrayToJsonString(input);
-    assertTrue(actualOutput.equals(expectedOutput1) || actualOutput.equals(expectedOutput2));
-  }
 }
diff --git a/cpp/src/lookup_key.cc b/cpp/src/lookup_key.cc
index d793a2b..0052cb5 100644
--- a/cpp/src/lookup_key.cc
+++ b/cpp/src/lookup_key.cc
@@ -90,8 +90,15 @@
   } else {
     for (size_t i = 0; i < arraysize(kHierarchy); ++i) {
       AddressField field = kHierarchy[i];
+      if (address.IsFieldEmpty(field)) {
+        // It would be impossible to find any data for an empty field value.
+        break;
+      }
       const std::string& value = address.GetFieldValue(field);
-      if (value.empty()) {
+      if (value.find('/') != std::string::npos) {
+        // The address metadata server does not have data for any fields with a
+        // slash in their value. The slash is used as a syntax character in the
+        // lookup key format.
         break;
       }
       nodes_.insert(std::make_pair(field, value));
diff --git a/cpp/src/region_data_constants.cc b/cpp/src/region_data_constants.cc
index a44a310..783ecf2 100644
--- a/cpp/src/region_data_constants.cc
+++ b/cpp/src/region_data_constants.cc
@@ -291,6 +291,7 @@
       "}"));
   region_data.insert(std::make_pair("CO", "{"
       "\"fmt\":\"%N%n%O%n%A%n%C, %S, %Z\","
+      "\"require\":\"AS\","
       "\"zipex\":\"111221,130001,760011\","
       "\"posturl\":\"http://www.codigopostal.gov.co/\","
       "\"state_name_type\":\"department\","
@@ -568,13 +569,14 @@
       "}"));
   region_data.insert(std::make_pair("HU", "{"
       "\"fmt\":\"%N%n%O%n%C%n%A%n%Z\","
+      "\"require\":\"ACZ\","
       "\"zipex\":\"1037,2380,1540\","
       "\"posturl\":\"http://posta.hu/ugyfelszolgalat/iranyitoszam_kereso\","
       "\"languages\":\"hu\""
       "}"));
   region_data.insert(std::make_pair("ID", "{"
       "\"fmt\":\"%N%n%O%n%A%n%C%n%S %Z\","
-      "\"state_name_type\":\"district\","
+      "\"require\":\"AS\","
       "\"zipex\":\"40115\","
       "\"languages\":\"id\""
       "}"));
diff --git a/cpp/test/lookup_key_test.cc b/cpp/test/lookup_key_test.cc
index 3f1fab6..f66ca01 100644
--- a/cpp/test/lookup_key_test.cc
+++ b/cpp/test/lookup_key_test.cc
@@ -89,6 +89,18 @@
   EXPECT_EQ("data/111/222", lookup_key.ToKeyString(kMaxDepth));
 }
 
+TEST(LookupKeyTest, AddressDepthTerminateOnSlash) {
+  AddressData address;
+  address.region_code = "111";
+  address.administrative_area = "222";
+  address.locality = "3/3";  // No data should be requested for this LOCALITY.
+  address.dependent_locality = "444";
+  LookupKey lookup_key;
+  lookup_key.FromAddress(address);
+  EXPECT_EQ(1, lookup_key.GetDepth());
+  EXPECT_EQ("data/111/222", lookup_key.ToKeyString(kMaxDepth));
+}
+
 TEST(LookupKeyTest, RequestDepth) {
   AddressData address;
   address.region_code = "111";