/*
 * Copyright (c) 2007 Sun Microsystems, Inc.  All Rights Reserved.
 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
 *
 * This code is free software; you can redistribute it and/or modify it
 * under the terms of the GNU General Public License version 2 only, as
 * published by the Free Software Foundation.
 *
 * This code is distributed in the hope that it will be useful, but WITHOUT
 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
 * version 2 for more details (a copy is included in the LICENSE file that
 * accompanied this code).
 *
 * You should have received a copy of the GNU General Public License version
 * 2 along with this work; if not, write to the Free Software Foundation,
 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
 *
 * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
 * CA 95054 USA or visit www.sun.com if you need additional information or
 * have any questions.
 */

/**
 * @test
 * @bug 4640234 4946057 4938151 4873691 5023181
 * @summary Verifies the translation of time zone names, this test will catch presence
 *          of country name for english and selected locales for all ISO country
 *          codes.
 *          The test program also displays which timezone, country and language names
 *          are not translated
 */


/*
 * 4946057 Localization for ISO country & language data.
 * 4938151 Time zones not translated
 * 4873691 Changes in TimeZone mapping
 */

import java.text.MessageFormat;
import java.text.SimpleDateFormat;

import java.util.Date;
import java.util.Locale;
import java.util.Enumeration;
import java.util.HashMap;
import java.util.Map;
import java.util.ResourceBundle;
import java.util.TimeZone;


public class Bug4640234  {
  static SimpleDateFormat sdfEn = new SimpleDateFormat("zzzz", Locale.US);
  static SimpleDateFormat sdfEnShort = new SimpleDateFormat("z", Locale.US);
  static Locale locEn = Locale.ENGLISH;

  static SimpleDateFormat sdfLoc;
  static SimpleDateFormat sdfLocShort;
  static Date date = new Date();

  // Define supported locales
  static Locale[] locales2Test = new Locale[] {
    new Locale("de"),
    new Locale("es"),
    new Locale("fr"),
    new Locale("it"),
    new Locale("ja"),
    new Locale("ko"),
    new Locale("sv"),
    new Locale("zh", "CN"),
    new Locale("zh", "TW")
  };

  public static void main(String[] args) throws Exception {
    Locale.setDefault(Locale.ENGLISH);

    StringBuffer errors = new StringBuffer("");
    StringBuffer warnings = new StringBuffer("");

    String[] timezones = TimeZone.getAvailableIDs();
    String[] countries = locEn.getISOCountries();
    String[] languages = locEn.getISOLanguages();

    ResourceBundle resEn = ResourceBundle.getBundle("sun.util.resources.LocaleNames", locEn);
    Map<String, String> countryMapEn = getList(resEn, true);
    Map<String, String> languageMapEn = getList(resEn, false);

    ResourceBundle resLoc;
    Map<String, String> countryMap;
    Map<String, String> languageMap;

    for (Locale locale : locales2Test) {
      resLoc = ResourceBundle.getBundle("sun.util.resources.LocaleNames", locale);

      sdfLoc = new SimpleDateFormat("zzzz", locale);
      sdfLocShort = new SimpleDateFormat("z", locale);

      for (String timezone : timezones) {
        if (isTZIgnored(timezone)) {
          continue;
        }
        warnings.append(testTZ(timezone, locale));
      }

      countryMap = getList(resLoc, true);

      for (String country : countries) {
        String[] result = testEntry(country,
          countryMapEn,
          countryMap,
          locale,
          "ERROR: {0} country name for country code: {1} not found!\n",
          "WARNING: {0} country name for country code: {1} not localized!\n"
        );
        if (warnings.indexOf(result[0]) == -1) {
          warnings.append(result[0]);
        }
        if (errors.indexOf(result[1]) == -1) {
          errors.append(result[1]);
        }
      }

      languageMap = getList(resLoc, false);
      for (String language : languages) {
        String[] result = testEntry(language,
          languageMapEn,
          languageMap,
          locale,
          "ERROR: {0} language name for language code: {1} not found!\n",
          "WARNING: {0} language name for language code: {1} not localized!\n");
        if (warnings.indexOf(result[0]) == -1) {
          warnings.append(result[0]);
        }
        if (errors.indexOf(result[1]) == -1) {
          errors.append(result[1]);
        }
      }
    }

    StringBuffer message = new StringBuffer("");
    if (!"".equals(errors.toString())) {
      message.append("Test failed! ");
      message.append("ERROR: some keys are missing! ");
    }

    if ("".equals(message.toString())) {
      System.out.println("\nTest passed");
      System.out.println(warnings.toString());
    } else {
      System.out.println("\nTest failed!");
      System.out.println(errors.toString());
      System.out.println(warnings.toString());
      throw new Exception("\n" + message);
    }
  }

  /**
  * Compares the english timezone name and timezone name in specified locale
  * @param timeZoneName - name of the timezone to compare
  * @param locale - locale to test against english
  * @return empty string when passed, descriptive error message in other cases
  */
  private static String testTZ(String timeZoneName, Locale locale) {
    StringBuffer timeZoneResult = new StringBuffer("");
    TimeZone tz = TimeZone.getTimeZone(timeZoneName);
    sdfEn.setTimeZone(tz);
    sdfEnShort.setTimeZone(tz);
    sdfLoc.setTimeZone(tz);
    sdfLocShort.setTimeZone(tz);

    String en, enShort, loc, locShort;
    en = sdfEn.format(date);
    enShort = sdfEnShort.format(date);
    loc = sdfLoc.format(date);
    locShort = sdfLocShort.format(date);

    String displayLanguage = locale.getDisplayLanguage();
    String displayCountry = locale.getDisplayCountry();

    if (loc.equals(en)) {
      timeZoneResult.append("[");
      timeZoneResult.append(displayLanguage);
      if (!"".equals(displayCountry)) {
        timeZoneResult.append(" ");
        timeZoneResult.append(displayCountry);
      }
      timeZoneResult.append("] timezone \"");
      timeZoneResult.append(timeZoneName);
      timeZoneResult.append("\" long name \"" + en);
      timeZoneResult.append("\" not localized!\n");
    }

    if (!locShort.equals(enShort)) {
      timeZoneResult.append("[");
      timeZoneResult.append(displayLanguage);
      if (!"".equals(displayCountry)) {
        timeZoneResult.append(" ");
        timeZoneResult.append(displayCountry);
      }
      timeZoneResult.append("] timezone \"");
      timeZoneResult.append(timeZoneName);
      timeZoneResult.append("\" short name \"" + enShort);
      timeZoneResult.append("\" is localized \"");
      timeZoneResult.append(locShort);
      timeZoneResult.append("\"!\n");
    }
    return timeZoneResult.toString();
  }

  /**
  * Verifies whether the name for ISOCode is localized.
  * @param ISOCode - ISO country/language code for country/language name to test
  * @param entriesEn - array of english country/language names
  * @param entriesLoc - array of localized country/language names for specified locale
  * @param locale - locale to test against english
  * @param notFoundMessage - message in form ready for MessageFormat, {0} will be human readable
  *                          language name, {1} will be ISOCode.
  * @param notLocalizedMessage - message in for ready for MessageFormat, same formatting like
  *                              for notFountMessage
  * @return array of two empty strings when passed, descriptive error message in
  *         other cases, [0] - warnings for not localized, [1] - errors for missing keys.
  */
  private static String[] testEntry(String ISOCode,
                                    Map<String, String> entriesEn,
                                    Map<String, String> entriesLoc,
                                    Locale locale,
                                    String notFoundMessage,
                                    String notLocalizedMessage) {
    String nameEn = null;
    String nameLoc = null;

    for (String key: entriesEn.keySet()) {
      if (ISOCode.equalsIgnoreCase(key)) {
        nameEn = entriesEn.get(key);
        break;
      }
    }

    for (String key: entriesLoc.keySet()) {
      if (ISOCode.equalsIgnoreCase(key)) {
        nameLoc = entriesLoc.get(key);
        break;
      }
    }

    if (nameEn == null) {
      // We should not get here but test is a MUST have
      return new String[] {"", MessageFormat.format(notFoundMessage,
        new String[] {"English", ISOCode})};
    }

    if (nameLoc == null) {
      return new String[] {"", MessageFormat.format(notFoundMessage,
        new String[] {locale.getDisplayName(), ISOCode})};
    }

    if (nameEn.equals(nameLoc)) {
      return new String[] {MessageFormat.format(notLocalizedMessage,
        new String[] {locale.getDisplayName(), ISOCode}), ""};
    }

    return new String[] {"", ""};
  }

  private static boolean isTZIgnored(String TZName) {
    if (TZName.startsWith("Etc/GMT") ||
        TZName.indexOf("Riyadh8") != -1 ||
        TZName.equals("GMT0") ||
        TZName.equals("MET")
        ) {
      return true;
    }
    return false;
  }

    private static Map<String, String> getList(ResourceBundle rs, Boolean getCountryList) {
        char beginChar = 'a';
        char endChar = 'z';
        if (getCountryList) {
            beginChar = 'A';
            endChar = 'Z';
        }

        Map<String, String> hm = new HashMap<String, String>();
        Enumeration<String> keys = rs.getKeys();
        while (keys.hasMoreElements()) {
            String s = keys.nextElement();
            if (s.length() == 2 &&
                s.charAt(0) >= beginChar && s.charAt(0) <= endChar) {
                hm.put(s, rs.getString(s));
            }
        }
        return hm;
    }
}
