/*
**********************************************************************
* Copyright (c) 2003-2011 International Business Machines
* Corporation and others.  All Rights Reserved.
**********************************************************************
* Author: Alan Liu
* Created: September 4 2003
* Since: ICU 2.8
**********************************************************************
*/
package com.ibm.icu.impl;

import java.lang.ref.SoftReference;
import java.text.ParsePosition;
import java.util.Collections;
import java.util.Locale;
import java.util.MissingResourceException;
import java.util.Set;
import java.util.TreeSet;

import com.ibm.icu.text.NumberFormat;
import com.ibm.icu.util.SimpleTimeZone;
import com.ibm.icu.util.TimeZone;
import com.ibm.icu.util.TimeZone.SystemTimeZoneType;
import com.ibm.icu.util.UResourceBundle;

/**
 * This class, not to be instantiated, implements the meta-data
 * missing from the underlying core JDK implementation of time zones.
 * There are two missing features: Obtaining a list of available zones
 * for a given country (as defined by the Olson database), and
 * obtaining a list of equivalent zones for a given zone (as defined
 * by Olson links).
 *
 * This class uses a data class, ZoneMetaData, which is created by the
 * tool tz2icu.
 *
 * @author Alan Liu
 * @since ICU 2.8
 */
public final class ZoneMeta {
    private static final boolean ASSERT = false;

    private static final String ZONEINFORESNAME = "zoneinfo64";
    private static final String kREGIONS  = "Regions";
    private static final String kZONES    = "Zones";
    private static final String kNAMES    = "Names";

    private static final String kGMT_ID   = "GMT";
    private static final String kCUSTOM_TZ_PREFIX = "GMT";

    private static final String kWorld = "001";

    private static SoftReference<Set<String>> REF_SYSTEM_ZONES;
    private static SoftReference<Set<String>> REF_CANONICAL_SYSTEM_ZONES;
    private static SoftReference<Set<String>> REF_CANONICAL_SYSTEM_LOCATION_ZONES;

    /**
     * Returns an immutable set of system time zone IDs.
     * Etc/Unknown is excluded.
     * @return An immutable set of system time zone IDs.
     */
    private static synchronized Set<String> getSystemZIDs() {
        Set<String> systemZones = null;
        if (REF_SYSTEM_ZONES != null) {
            systemZones = REF_SYSTEM_ZONES.get();
        }
        if (systemZones == null) {
            Set<String> systemIDs = new TreeSet<String>();
            String[] allIDs = getZoneIDs();
            for (String id : allIDs) {
                // exclude Etc/Unknown
                if (id.equals(TimeZone.UNKNOWN_ZONE_ID)) {
                    continue;
                }
                systemIDs.add(id);
            }
            systemZones = Collections.unmodifiableSet(systemIDs);
            REF_SYSTEM_ZONES = new SoftReference<Set<String>>(systemZones);
        }
        return systemZones;
    }

    /**
     * Returns an immutable set of canonical system time zone IDs.
     * The result set is a subset of {@link #getSystemZIDs()}, but not
     * including aliases, such as "US/Eastern".
     * @return An immutable set of canonical system time zone IDs.
     */
    private static synchronized Set<String> getCanonicalSystemZIDs() {
        Set<String> canonicalSystemZones = null;
        if (REF_CANONICAL_SYSTEM_ZONES != null) {
            canonicalSystemZones = REF_CANONICAL_SYSTEM_ZONES.get();
        }
        if (canonicalSystemZones == null) {
            Set<String> canonicalSystemIDs = new TreeSet<String>();
            String[] allIDs = getZoneIDs();
            for (String id : allIDs) {
                // exclude Etc/Unknown
                if (id.equals(TimeZone.UNKNOWN_ZONE_ID)) {
                    continue;
                }
                String canonicalID = getCanonicalCLDRID(id);
                if (id.equals(canonicalID)) {
                    canonicalSystemIDs.add(id);
                }
            }
            canonicalSystemZones = Collections.unmodifiableSet(canonicalSystemIDs);
            REF_CANONICAL_SYSTEM_ZONES = new SoftReference<Set<String>>(canonicalSystemZones);
        }
        return canonicalSystemZones;
    }

    /**
     * Returns an immutable set of canonical system time zone IDs that
     * are associated with actual locations.
     * The result set is a subset of {@link #getCanonicalSystemZIDs()}, but not
     * including IDs, such as "Etc/GTM+5".
     * @return An immutable set of canonical system time zone IDs that
     * are associated with actual locations.
     */
    private static synchronized Set<String> getCanonicalSystemLocationZIDs() {
        Set<String> canonicalSystemLocationZones = null;
        if (REF_CANONICAL_SYSTEM_LOCATION_ZONES != null) {
            canonicalSystemLocationZones = REF_CANONICAL_SYSTEM_LOCATION_ZONES.get();
        }
        if (canonicalSystemLocationZones == null) {
            Set<String> canonicalSystemLocationIDs = new TreeSet<String>();
            String[] allIDs = getZoneIDs();
            for (String id : allIDs) {
                // exclude Etc/Unknown
                if (id.equals(TimeZone.UNKNOWN_ZONE_ID)) {
                    continue;
                }
                String canonicalID = getCanonicalCLDRID(id);
                if (id.equals(canonicalID)) {
                    String region = getRegion(id);
                    if (region != null && !region.equals(kWorld)) {
                        canonicalSystemLocationIDs.add(id);
                    }
                }
            }
            canonicalSystemLocationZones = Collections.unmodifiableSet(canonicalSystemLocationIDs);
            REF_CANONICAL_SYSTEM_LOCATION_ZONES = new SoftReference<Set<String>>(canonicalSystemLocationZones);
        }
        return canonicalSystemLocationZones;
    }

    /**
     * Returns an immutable set of system IDs for the given conditions.
     * @param type      a system time zone type.
     * @param region    a region, or null.
     * @param rawOffset a zone raw offset or null.
     * @return An immutable set of system IDs for the given conditions.
     */
    public static Set<String> getAvailableIDs(SystemTimeZoneType type, String region, Integer rawOffset) {
        Set<String> baseSet = null;
        switch (type) {
        case ANY:
            baseSet = getSystemZIDs();
            break;
        case CANONICAL:
            baseSet = getCanonicalSystemZIDs();
            break;
        case CANONICAL_LOCATION:
            baseSet = getCanonicalSystemLocationZIDs();
            break;
        default:
            // never occur
            throw new IllegalArgumentException("Unknown SystemTimeZoneType");
        }

        if (region == null && rawOffset == null) {
            return baseSet;
        }

        if (region != null) {
            region = region.toUpperCase(Locale.ENGLISH);
        }

        // Filter by region/rawOffset
        Set<String> result = new TreeSet<String>();
        for (String id : baseSet) {
            if (region != null) {
                String r = getRegion(id);
                if (!region.equals(r)) {
                    continue;
                }
            }
            if (rawOffset != null) {
                // This is VERY inefficient.
                TimeZone z = getSystemTimeZone(id);
                if (z == null || !rawOffset.equals(z.getRawOffset())) {
                    continue;
                }
            }
            result.add(id);
        }
        if (result.isEmpty()) {
            return Collections.emptySet();
        }

        return Collections.unmodifiableSet(result);
    }

    /**
     * Returns the number of IDs in the equivalency group that
     * includes the given ID.  An equivalency group contains zones
     * that behave identically to the given zone.
     *
     * <p>If there are no equivalent zones, then this method returns
     * 0.  This means either the given ID is not a valid zone, or it
     * is and there are no other equivalent zones.
     * @param id a system time zone ID
     * @return the number of zones in the equivalency group containing
     * 'id', or zero if there are no equivalent zones.
     * @see #getEquivalentID
     */
    public static synchronized int countEquivalentIDs(String id) {
        int count = 0;
        try {
            UResourceBundle res = openOlsonResource(null, id);
            UResourceBundle links = res.get("links");
            int[] v = links.getIntVector();
            count = v.length;
        } catch (MissingResourceException ex) {
            // throw away
        }
        return count;
    }

    /**
     * Returns an ID in the equivalency group that includes the given
     * ID.  An equivalency group contains zones that behave
     * identically to the given zone.
     *
     * <p>The given index must be in the range 0..n-1, where n is the
     * value returned by <code>countEquivalentIDs(id)</code>.  For
     * some value of 'index', the returned value will be equal to the
     * given id.  If the given id is not a valid system time zone, or
     * if 'index' is out of range, then returns an empty string.
     * @param id a system time zone ID
     * @param index a value from 0 to n-1, where n is the value
     * returned by <code>countEquivalentIDs(id)</code>
     * @return the ID of the index-th zone in the equivalency group
     * containing 'id', or an empty string if 'id' is not a valid
     * system ID or 'index' is out of range
     * @see #countEquivalentIDs
     */
    public static synchronized String getEquivalentID(String id, int index) {
        String result = "";
        int zoneIdx = -1;

        if (index >= 0) {
            try {
                UResourceBundle res = openOlsonResource(null, id);
                UResourceBundle links = res.get("links");
                int[] zones = links.getIntVector();
                if (index < zones.length) {
                    zoneIdx = zones[index];
                }
            } catch (MissingResourceException ex) {
                // throw away
                zoneIdx = -1;
            }
        }
        if (zoneIdx >= 0) {
            String tmp = getZoneID(zoneIdx);
            if (tmp != null) {
                result = tmp;
            }
        }
        return result;
    }

    private static String[] ZONEIDS = null;

    /*
     * ICU frequently refers the zone ID array in zoneinfo resource
     */
    private static synchronized String[] getZoneIDs() {
        if (ZONEIDS == null) {
            try {
                UResourceBundle top = UResourceBundle.getBundleInstance(
                        ICUResourceBundle.ICU_BASE_NAME, ZONEINFORESNAME, ICUResourceBundle.ICU_DATA_CLASS_LOADER);
                UResourceBundle names = top.get(kNAMES);
                ZONEIDS = names.getStringArray();
            } catch (MissingResourceException ex) {
                // throw away..
            }
        }
        if (ZONEIDS == null) {
            ZONEIDS = new String[0];
        }
        return ZONEIDS;
    }

    private static String getZoneID(int idx) {
        if (idx >= 0) {
            String[] ids = getZoneIDs();
            if (idx < ids.length) {
                return ids[idx];
            }
        }
        return null;
    }

    private static int getZoneIndex(String zid) {
        int zoneIdx = -1;

        String[] all = getZoneIDs();
        if (all.length > 0) {
            int start = 0;
            int limit = all.length;

            int lastMid = Integer.MAX_VALUE;
            for (;;) {
                int mid = (start + limit) / 2;
                if (lastMid == mid) {   /* Have we moved? */
                    break;  /* We haven't moved, and it wasn't found. */
                }
                lastMid = mid;
                int r = zid.compareTo(all[mid]);
                if (r == 0) {
                    zoneIdx = mid;
                    break;
                } else if(r < 0) {
                    limit = mid;
                } else {
                    start = mid;
                }
            }
        }

        return zoneIdx;
    }

    private static ICUCache<String, String> CANONICAL_ID_CACHE = new SimpleCache<String, String>();
    private static ICUCache<String, String> REGION_CACHE = new SimpleCache<String, String>();
    private static ICUCache<String, Boolean> SINGLE_COUNTRY_CACHE = new SimpleCache<String, Boolean>();

    public static String getCanonicalCLDRID(TimeZone tz) {
        if (tz instanceof OlsonTimeZone) {
            return ((OlsonTimeZone)tz).getCanonicalID();
        }
        return getCanonicalCLDRID(tz.getID());
    }

    /**
     * Return the canonical id for this tzid defined by CLDR, which might be
     * the id itself. If the given tzid is not known, return null.
     * 
     * Note: This internal API supports all known system IDs and "Etc/Unknown" (which is
     * NOT a sysmte ID).
     */
    public static String getCanonicalCLDRID(String tzid) {
        String canonical = CANONICAL_ID_CACHE.get(tzid);
        if (canonical == null) {
            int zoneIdx = getZoneIndex(tzid);
            if (zoneIdx >= 0) {
                try {
                    UResourceBundle top = UResourceBundle.getBundleInstance(
                            ICUResourceBundle.ICU_BASE_NAME, ZONEINFORESNAME, ICUResourceBundle.ICU_DATA_CLASS_LOADER);
                    UResourceBundle zones = top.get(kZONES);
                    UResourceBundle zone = zones.get(zoneIdx);
                    if (zone.getType() == UResourceBundle.INT) {
                        // resolve link
                        String tmp = getZoneID(zone.getInt());
                        if (tmp != null) {
                            canonical = tmp;
                        }
                    } else {
                        canonical = tzid;
                    }
                    // check canonical mapping in CLDR
                    UResourceBundle keyTypeData = UResourceBundle.getBundleInstance(
                            ICUResourceBundle.ICU_BASE_NAME, "keyTypeData", ICUResourceBundle.ICU_DATA_CLASS_LOADER);
                    UResourceBundle typeAlias = keyTypeData.get("typeAlias");
                    UResourceBundle aliasesForKey = typeAlias.get("timezone");
                    String cldrCanonical = aliasesForKey.getString(canonical.replace('/', ':'));
                    if (cldrCanonical != null) {
                        canonical = cldrCanonical;
                    }
                } catch (MissingResourceException e) {
                    // fall through
                }
            }
            if (canonical != null) {
                CANONICAL_ID_CACHE.put(tzid, canonical);
            }
        }
        return canonical;
    }

    /**
     * Return the region code for this tzid.
     * If tzid is not a system zone ID, this method returns null.
     */
    public static String getRegion(String tzid) {
        String region = REGION_CACHE.get(tzid);
        if (region == null) {
            int zoneIdx = getZoneIndex(tzid);
            if (zoneIdx >= 0) {
                try {
                    UResourceBundle top = UResourceBundle.getBundleInstance(
                            ICUResourceBundle.ICU_BASE_NAME, ZONEINFORESNAME, ICUResourceBundle.ICU_DATA_CLASS_LOADER);
                    UResourceBundle regions = top.get(kREGIONS);
                    if (zoneIdx < regions.getSize()) {
                        region = regions.getString(zoneIdx);
                    }
                } catch (MissingResourceException e) {
                    // throw away
                }
                if (region != null) {
                    REGION_CACHE.put(tzid, region);
                }
            }
        }
        return region;
    }

    /**
     * Return the canonical country code for this tzid.  If we have none, or if the time zone
     * is not associated with a country or unknown, return null.
     */
    public static String getCanonicalCountry(String tzid) {
        String country = getRegion(tzid);
        if (country != null && country.equals(kWorld)) {
            country = null;
        }
        return country;
    }

    /**
     * Return the country code if this is a 'single' time zone that can fallback to just
     * the country, otherwise return null.  (Note, one must also check the locale data
     * to see that there is a localization for the country in order to implement
     * tr#35 appendix J step 5.)
     */
    public static String getSingleCountry(String tzid) {
        String country = getCanonicalCountry(tzid);
        if (country != null) {
            Boolean isSingle = SINGLE_COUNTRY_CACHE.get(tzid);
            if (isSingle == null) {
                Set<String> ids = TimeZone.getAvailableIDs(SystemTimeZoneType.CANONICAL_LOCATION, country, null);
                assert(ids.size() >= 1);
                isSingle = Boolean.valueOf(ids.size() <= 1);
                SINGLE_COUNTRY_CACHE.put(tzid, isSingle);
            }
            if (!isSingle) {
                country = null;
            }
        }
        return country;
    }

    /**
     * Given an ID and the top-level resource of the zoneinfo resource,
     * open the appropriate resource for the given time zone.
     * Dereference links if necessary.
     * @param top the top level resource of the zoneinfo resource or null.
     * @param id zone id
     * @return the corresponding zone resource or null if not found
     */
    public static UResourceBundle openOlsonResource(UResourceBundle top, String id)
    {
        UResourceBundle res = null;
        int zoneIdx = getZoneIndex(id);
        if (zoneIdx >= 0) {
            try {
                if (top == null) {
                    top = UResourceBundle.getBundleInstance(
                            ICUResourceBundle.ICU_BASE_NAME, ZONEINFORESNAME, ICUResourceBundle.ICU_DATA_CLASS_LOADER);
                }
                UResourceBundle zones = top.get(kZONES);
                UResourceBundle zone = zones.get(zoneIdx);
                if (zone.getType() == UResourceBundle.INT) {
                    // resolve link
                    zone = zones.get(zone.getInt());
                }
                res = zone;
            } catch (MissingResourceException e) {
                res = null;
            }
        }
        return res;
    }


    private static ICUCache<String, TimeZone> SYSTEM_ZONE_CACHE = new SimpleCache<String, TimeZone>();

    /**
     * Lookup the given name in our system zone table.  If found,
     * instantiate a new zone of that name and return it.  If not
     * found, return 0.
     */
    public static TimeZone getSystemTimeZone(String id) {
        TimeZone z = SYSTEM_ZONE_CACHE.get(id);
        if (z == null) {
            try{
                UResourceBundle top = UResourceBundle.getBundleInstance(
                        ICUResourceBundle.ICU_BASE_NAME, ZONEINFORESNAME, ICUResourceBundle.ICU_DATA_CLASS_LOADER);
                UResourceBundle res = openOlsonResource(top, id);
                z = new OlsonTimeZone(top, res, id);
                SYSTEM_ZONE_CACHE.put(id, z);
            }catch(Exception ex){
                return null;
            }
        }
        return (TimeZone)z.clone();
    }

    // Maximum value of valid custom time zone hour/min
    private static final int kMAX_CUSTOM_HOUR = 23;
    private static final int kMAX_CUSTOM_MIN = 59;
    private static final int kMAX_CUSTOM_SEC = 59;

    /**
     * Parse a custom time zone identifier and return a corresponding zone.
     * @param id a string of the form GMT[+-]hh:mm, GMT[+-]hhmm, or
     * GMT[+-]hh.
     * @return a newly created SimpleTimeZone with the given offset and
     * no Daylight Savings Time, or null if the id cannot be parsed.
    */
    public static TimeZone getCustomTimeZone(String id){
        int[] fields = new int[4];
        if (parseCustomID(id, fields)) {
            String zid = formatCustomID(fields[1], fields[2], fields[3], fields[0] < 0);
            int offset = fields[0] * ((fields[1] * 60 + fields[2]) * 60 + fields[3]) * 1000;
            return new SimpleTimeZone(offset, zid);
        }
        return null;
    }

    /**
     * Parse a custom time zone identifier and return the normalized
     * custom time zone identifier for the given custom id string.
     * @param id a string of the form GMT[+-]hh:mm, GMT[+-]hhmm, or
     * GMT[+-]hh.
     * @return The normalized custom id string.
    */
    public static String getCustomID(String id) {
        int[] fields = new int[4];
        if (parseCustomID(id, fields)) {
            return formatCustomID(fields[1], fields[2], fields[3], fields[0] < 0);
        }
        return null;
    }

    /*
     * Parses the given custom time zone identifier
     * @param id id A string of the form GMT[+-]hh:mm, GMT[+-]hhmm, or
     * GMT[+-]hh.
     * @param fields An array of int (length = 4) to receive the parsed
     * offset time fields.  The sign is set to fields[0] (-1 or 1),
     * hour is set to fields[1], minute is set to fields[2] and second is
     * set to fields[3].
     * @return Returns true when the given custom id is valid.
     */
    static boolean parseCustomID(String id, int[] fields) {
        NumberFormat numberFormat = null;
        String idUppercase = id.toUpperCase(Locale.ENGLISH);

        if (id != null && id.length() > kGMT_ID.length() &&
            idUppercase.startsWith(kGMT_ID)) {
            ParsePosition pos = new ParsePosition(kGMT_ID.length());
            int sign = 1;
            int hour = 0;
            int min = 0;
            int sec = 0;

            if (id.charAt(pos.getIndex()) == 0x002D /*'-'*/) {
                sign = -1;
            } else if (id.charAt(pos.getIndex()) != 0x002B /*'+'*/) {
                return false;
            }
            pos.setIndex(pos.getIndex() + 1);

            numberFormat = NumberFormat.getInstance();
            numberFormat.setParseIntegerOnly(true);

            // Look for either hh:mm, hhmm, or hh
            int start = pos.getIndex();

            Number n = numberFormat.parse(id, pos);
            if (pos.getIndex() == start) {
                return false;
            }
            hour = n.intValue();

            if (pos.getIndex() < id.length()){
                if (pos.getIndex() - start > 2
                        || id.charAt(pos.getIndex()) != 0x003A /*':'*/) {
                    return false;
                }
                // hh:mm
                pos.setIndex(pos.getIndex() + 1);
                int oldPos = pos.getIndex();
                n = numberFormat.parse(id, pos);
                if ((pos.getIndex() - oldPos) != 2) {
                    // must be 2 digits
                    return false;
                }
                min = n.intValue();
                if (pos.getIndex() < id.length()) {
                    if (id.charAt(pos.getIndex()) != 0x003A /*':'*/) {
                        return false;
                    }
                    // [:ss]
                    pos.setIndex(pos.getIndex() + 1);
                    oldPos = pos.getIndex();
                    n = numberFormat.parse(id, pos);
                    if (pos.getIndex() != id.length()
                            || (pos.getIndex() - oldPos) != 2) {
                        return false;
                    }
                    sec = n.intValue();
                }
            } else {
                // Supported formats are below -
                //
                // HHmmss
                // Hmmss
                // HHmm
                // Hmm
                // HH
                // H

                int length = pos.getIndex() - start;
                if (length <= 0 || 6 < length) {
                    // invalid length
                    return false;
                }
                switch (length) {
                    case 1:
                    case 2:
                        // already set to hour
                        break;
                    case 3:
                    case 4:
                        min = hour % 100;
                        hour /= 100;
                        break;
                    case 5:
                    case 6:
                        sec = hour % 100;
                        min = (hour/100) % 100;
                        hour /= 10000;
                        break;
                }
            }

            if (hour <= kMAX_CUSTOM_HOUR && min <= kMAX_CUSTOM_MIN && sec <= kMAX_CUSTOM_SEC) {
                if (fields != null) {
                    if (fields.length >= 1) {
                        fields[0] = sign;
                    }
                    if (fields.length >= 2) {
                        fields[1] = hour;
                    }
                    if (fields.length >= 3) {
                        fields[2] = min;
                    }
                    if (fields.length >= 4) {
                        fields[3] = sec;
                    }
                }
                return true;
            }
        }
        return false;
    }

    /**
     * Creates a custom zone for the offset
     * @param offset GMT offset in milliseconds
     * @return A custom TimeZone for the offset with normalized time zone id
     */
    public static TimeZone getCustomTimeZone(int offset) {
        boolean negative = false;
        int tmp = offset;
        if (offset < 0) {
            negative = true;
            tmp = -offset;
        }

        int hour, min, sec, millis;

        millis = tmp % 1000;
        if (ASSERT) {
            Assert.assrt("millis!=0", millis != 0);
        }
        tmp /= 1000;
        sec = tmp % 60;
        tmp /= 60;
        min = tmp % 60;
        hour = tmp / 60;

        // Note: No millisecond part included in TZID for now
        String zid = formatCustomID(hour, min, sec, negative);

        return new SimpleTimeZone(offset, zid);
    }

    /*
     * Returns the normalized custom TimeZone ID
     */
    static String formatCustomID(int hour, int min, int sec, boolean negative) {
        // Create normalized time zone ID - GMT[+|-]hh:mm[:ss]
        StringBuilder zid = new StringBuilder(kCUSTOM_TZ_PREFIX);
        if (hour != 0 || min != 0) {
            if(negative) {
                zid.append('-');
            } else {
                zid.append('+');
            }
            // Always use US-ASCII digits
            if (hour < 10) {
                zid.append('0');
            }
            zid.append(hour);
            zid.append(':');
            if (min < 10) {
                zid.append('0');
            }
            zid.append(min);

            if (sec != 0) {
                // Optional second field
                zid.append(':');
                if (sec < 10) {
                    zid.append('0');
                }
                zid.append(sec);
            }
        }
        return zid.toString();
    }
}
