8176841: Additional Unicode Language-Tag Extensions

8189134: New system properties for the default Locale extensions
8190918: Retrieve the region specific data regardless of language in locale
8191349: Add a new method in j.t.f.DateTimeFormatter to reflect Unicode extensions

Reviewed-by: scolebourne, lancea, rriggs, rgoel, nishjain
This commit is contained in:
Naoto Sato 2017-12-12 10:21:58 -08:00
parent 3246c46f41
commit f065141ddc
55 changed files with 3631 additions and 890 deletions

View file

@ -0,0 +1,106 @@
/*
* Copyright (c) 2017, Oracle and/or its affiliates. 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. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* 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 Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
package sun.util.cldr;
import static sun.util.locale.provider.LocaleProviderAdapter.Type;
import java.util.Arrays;
import java.util.Map;
import java.util.Locale;
import java.util.Set;
import java.util.Optional;
import java.util.concurrent.ConcurrentHashMap;
import sun.util.locale.provider.LocaleProviderAdapter;
import sun.util.locale.provider.LocaleResources;
import sun.util.locale.provider.CalendarDataProviderImpl;
import sun.util.locale.provider.CalendarDataUtility;
/**
* Concrete implementation of the
* {@link java.util.spi.CalendarDataProvider CalendarDataProvider} class
* for the CLDR LocaleProviderAdapter.
*
* @author Naoto Sato
*/
public class CLDRCalendarDataProviderImpl extends CalendarDataProviderImpl {
private static Map<String, Integer> firstDay = new ConcurrentHashMap<>();
private static Map<String, Integer> minDays = new ConcurrentHashMap<>();
public CLDRCalendarDataProviderImpl(Type type, Set<String> langtags) {
super(type, langtags);
}
@Override
public int getFirstDayOfWeek(Locale locale) {
return findValue(CalendarDataUtility.FIRST_DAY_OF_WEEK, locale);
}
@Override
public int getMinimalDaysInFirstWeek(Locale locale) {
return findValue(CalendarDataUtility.MINIMAL_DAYS_IN_FIRST_WEEK, locale);
}
/**
* Finds the requested integer value for the locale.
* Each resource consists of the following:
*
* (n: cc1 cc2 ... ccx;)*
*
* where 'n' is the integer for the following region codes, terminated by
* a ';'.
*
*/
private static int findValue(String key, Locale locale) {
Map<String, Integer> map = CalendarDataUtility.FIRST_DAY_OF_WEEK.equals(key) ?
firstDay : minDays;
String region = locale.getCountry();
if (region.isEmpty()) {
return 0;
}
Integer val = map.get(region);
if (val == null) {
String valStr =
LocaleProviderAdapter.forType(Type.CLDR).getLocaleResources(Locale.ROOT)
.getCalendarData(key);
val = retrieveInteger(valStr, region)
.orElse(retrieveInteger(valStr, "001").orElse(0));
map.putIfAbsent(region, val);
}
return val;
}
private static Optional<Integer> retrieveInteger(String src, String region) {
return Arrays.stream(src.split(";"))
.filter(entry -> entry.contains(region))
.map(entry -> entry.substring(0, entry.indexOf(":")))
.findAny()
.map(Integer::parseInt);
}
}

View file

@ -27,6 +27,7 @@ package sun.util.cldr;
import java.security.AccessController;
import java.security.AccessControlException;
import java.security.PrivilegedAction;
import java.security.PrivilegedActionException;
import java.security.PrivilegedExceptionAction;
import java.text.spi.BreakIteratorProvider;
@ -37,15 +38,16 @@ import java.util.HashSet;
import java.util.List;
import java.util.Locale;
import java.util.Map;
import java.util.Objects;
import java.util.Optional;
import java.util.ServiceLoader;
import java.util.ServiceConfigurationError;
import java.util.Set;
import java.util.StringTokenizer;
import java.util.concurrent.ConcurrentHashMap;
import java.util.spi.CalendarDataProvider;
import sun.util.locale.provider.JRELocaleProviderAdapter;
import sun.util.locale.provider.LocaleProviderAdapter;
import sun.util.locale.provider.LocaleDataMetaInfo;
import sun.util.locale.provider.LocaleProviderAdapter;
/**
* LocaleProviderAdapter implementation for the CLDR locale data.
@ -105,6 +107,24 @@ public class CLDRLocaleProviderAdapter extends JRELocaleProviderAdapter {
return null;
}
@Override
public CalendarDataProvider getCalendarDataProvider() {
if (calendarDataProvider == null) {
CalendarDataProvider provider = AccessController.doPrivileged(
(PrivilegedAction<CalendarDataProvider>) () ->
new CLDRCalendarDataProviderImpl(
getAdapterType(),
getLanguageTagSet("CalendarData")));
synchronized (this) {
if (calendarDataProvider == null) {
calendarDataProvider = provider;
}
}
}
return calendarDataProvider;
}
@Override
public CollatorProvider getCollatorProvider() {
return null;
@ -123,6 +143,10 @@ public class CLDRLocaleProviderAdapter extends JRELocaleProviderAdapter {
@Override
protected Set<String> createLanguageTagSet(String category) {
// Assume all categories support the same set as AvailableLocales
// in CLDR adapter.
category = "AvailableLocales";
// Directly call Base tags, as we know it's in the base module.
String supportedLocaleString = baseMetaInfo.availableLanguageTags(category);
String nonBaseTags = null;
@ -220,4 +244,11 @@ public class CLDRLocaleProviderAdapter extends JRELocaleProviderAdapter {
|| langtags.contains(locale.stripExtensions().toLanguageTag())
|| langtags.contains(getEquivalentLoc(locale).toLanguageTag());
}
/**
* Returns the time zone ID from an LDML's short ID
*/
public Optional<String> getTimeZoneID(String shortID) {
return Optional.ofNullable(baseMetaInfo.tzShortIDs().get(shortID));
}
}

View file

@ -1,5 +1,5 @@
/*
* Copyright (c) 2012, 2013, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2012, 2017, Oracle and/or its affiliates. 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
@ -46,14 +46,16 @@ public class CalendarDataProviderImpl extends CalendarDataProvider implements Av
@Override
public int getFirstDayOfWeek(Locale locale) {
return LocaleProviderAdapter.forType(type).getLocaleResources(locale)
String fw = LocaleProviderAdapter.forType(type).getLocaleResources(locale)
.getCalendarData(CalendarDataUtility.FIRST_DAY_OF_WEEK);
return convertToCalendarData(fw);
}
@Override
public int getMinimalDaysInFirstWeek(Locale locale) {
return LocaleProviderAdapter.forType(type).getLocaleResources(locale)
String md = LocaleProviderAdapter.forType(type).getLocaleResources(locale)
.getCalendarData(CalendarDataUtility.MINIMAL_DAYS_IN_FIRST_WEEK);
return convertToCalendarData(md);
}
@Override
@ -65,4 +67,9 @@ public class CalendarDataProviderImpl extends CalendarDataProvider implements Av
public Set<String> getAvailableLanguageTags() {
return langtags;
}
private int convertToCalendarData(String src) {
int val = Integer.parseInt(src);
return (src.isEmpty() || val <= 0 || val > 7) ? 0 : val;
}
}

View file

@ -1,5 +1,5 @@
/*
* Copyright (c) 2012, 2013, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2012, 2017, Oracle and/or its affiliates. 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
@ -47,10 +47,34 @@ public class CalendarDataUtility {
}
public static int retrieveFirstDayOfWeek(Locale locale) {
// Look for the Unicode Extension in the locale parameter
if (locale.hasExtensions()) {
String fw = locale.getUnicodeLocaleType("fw");
if (fw != null) {
switch (fw.toLowerCase(Locale.ROOT)) {
case "mon":
return MONDAY;
case "tue":
return TUESDAY;
case "wed":
return WEDNESDAY;
case "thu":
return THURSDAY;
case "fri":
return FRIDAY;
case "sat":
return SATURDAY;
case "sun":
return SUNDAY;
}
}
}
LocaleServiceProviderPool pool =
LocaleServiceProviderPool.getPool(CalendarDataProvider.class);
Integer value = pool.getLocalizedObject(CalendarWeekParameterGetter.INSTANCE,
locale, true, FIRST_DAY_OF_WEEK);
findRegionOverride(locale),
true, FIRST_DAY_OF_WEEK);
return (value != null && (value >= SUNDAY && value <= SATURDAY)) ? value : SUNDAY;
}
@ -58,7 +82,8 @@ public class CalendarDataUtility {
LocaleServiceProviderPool pool =
LocaleServiceProviderPool.getPool(CalendarDataProvider.class);
Integer value = pool.getLocalizedObject(CalendarWeekParameterGetter.INSTANCE,
locale, true, MINIMAL_DAYS_IN_FIRST_WEEK);
findRegionOverride(locale),
true, MINIMAL_DAYS_IN_FIRST_WEEK);
return (value != null && (value >= 1 && value <= 7)) ? value : 1;
}
@ -102,6 +127,32 @@ public class CalendarDataUtility {
return map;
}
/**
* Utility to look for a region override extension.
* If no region override is found, returns the original locale.
*/
public static Locale findRegionOverride(Locale l) {
String rg = l.getUnicodeLocaleType("rg");
Locale override = l;
if (rg != null && rg.length() == 6) {
// UN M.49 code should not be allowed here
// cannot use regex here, as it could be a recursive call
rg = rg.toUpperCase(Locale.ROOT);
if (rg.charAt(0) >= 0x0041 &&
rg.charAt(0) <= 0x005A &&
rg.charAt(1) >= 0x0041 &&
rg.charAt(1) <= 0x005A &&
rg.substring(2).equals("ZZZZ")) {
override = new Locale.Builder().setLocale(l)
.setRegion(rg.substring(0, 2))
.build();
}
}
return override;
}
static String normalizeCalendarType(String requestID) {
String type;
if (requestID.equals("gregorian") || requestID.equals("iso8601")) {
@ -179,7 +230,7 @@ public class CalendarDataUtility {
}
}
private static class CalendarWeekParameterGetter
private static class CalendarWeekParameterGetter
implements LocaleServiceProviderPool.LocalizedObjectGetter<CalendarDataProvider,
Integer> {
private static final CalendarWeekParameterGetter INSTANCE =

View file

@ -1,5 +1,5 @@
/*
* Copyright (c) 1999, 2012, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 1999, 2017, Oracle and/or its affiliates. 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
@ -32,6 +32,7 @@ import java.util.Calendar;
import java.util.Locale;
import java.util.MissingResourceException;
import java.util.Set;
import java.util.TimeZone;
/**
* Concrete implementation of the {@link java.text.spi.DateFormatProvider
@ -147,11 +148,14 @@ public class DateFormatProviderImpl extends DateFormatProvider implements Availa
throw new NullPointerException();
}
SimpleDateFormat sdf = new SimpleDateFormat("", locale);
// Check for region override
Locale rg = CalendarDataUtility.findRegionOverride(locale);
SimpleDateFormat sdf = new SimpleDateFormat("", rg);
Calendar cal = sdf.getCalendar();
try {
String pattern = LocaleProviderAdapter.forType(type)
.getLocaleResources(locale).getDateTimePattern(timeStyle, dateStyle,
.getLocaleResources(rg).getDateTimePattern(timeStyle, dateStyle,
cal);
sdf.applyPattern(pattern);
} catch (MissingResourceException mre) {
@ -159,6 +163,15 @@ public class DateFormatProviderImpl extends DateFormatProvider implements Availa
sdf.applyPattern("M/d/yy h:mm a");
}
// Check for timezone override
String tz = locale.getUnicodeLocaleType("tz");
if (tz != null) {
sdf.setTimeZone(
TimeZoneNameUtility.convertLDMLShortID(tz)
.map(TimeZone::getTimeZone)
.orElseGet(sdf::getTimeZone));
}
return sdf;
}

View file

@ -1,5 +1,5 @@
/*
* Copyright (c) 2012, 2016, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2012, 2017, Oracle and/or its affiliates. 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
@ -130,7 +130,7 @@ public class JRELocaleProviderAdapter extends LocaleProviderAdapter implements R
private volatile CurrencyNameProvider currencyNameProvider;
private volatile LocaleNameProvider localeNameProvider;
private volatile TimeZoneNameProvider timeZoneNameProvider;
private volatile CalendarDataProvider calendarDataProvider;
protected volatile CalendarDataProvider calendarDataProvider;
private volatile CalendarNameProvider calendarNameProvider;
private volatile CalendarProvider calendarProvider;

View file

@ -1,5 +1,5 @@
/*
* Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2014, 2017, Oracle and/or its affiliates. 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
@ -25,6 +25,8 @@
package sun.util.locale.provider;
import java.util.Map;
/**
* LocaleData meta info SPI
*
@ -46,4 +48,13 @@ public interface LocaleDataMetaInfo {
* @return concatenated language tags, separated by a space.
*/
public String availableLanguageTags(String category);
/**
* Returns a map for short time zone ids in BCP47 Unicode extension and
* the long time zone ids.
* @return map of short id to long ids, separated by a space.
*/
default public Map<String, String> tzShortIDs() {
return null;
}
}

View file

@ -1,5 +1,5 @@
/*
* Copyright (c) 2012, 2013, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2012, 2017, Oracle and/or its affiliates. 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
@ -168,6 +168,28 @@ public class LocaleNameProviderImpl extends LocaleNameProvider implements Availa
return getDisplayString("%%"+vrnt, locale);
}
/**
* @inheritDoc
*/
@Override
public String getDisplayUnicodeExtensionKey(String key, Locale locale) {
super.getDisplayUnicodeExtensionKey(key, locale); // null check
String rbKey = "key." + key;
String name = getDisplayString(rbKey, locale);
return rbKey.equals(name) ? key : name;
}
/**
* @inheritDoc
*/
@Override
public String getDisplayUnicodeExtensionType(String extType, String key, Locale locale) {
super.getDisplayUnicodeExtensionType(extType, key, locale); // null check
String rbKey = "type." + key + "." + extType;
String name = getDisplayString(rbKey, locale);
return rbKey.equals(name) ? extType : name;
}
private String getDisplayString(String key, Locale locale) {
if (key == null || locale == null) {
throw new NullPointerException();

View file

@ -1,5 +1,5 @@
/*
* Copyright (c) 2012, 2016, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2012, 2017, Oracle and/or its affiliates. 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
@ -122,23 +122,21 @@ public class LocaleResources {
return (byte[]) localeData.getBreakIteratorResources(locale).getObject(key);
}
int getCalendarData(String key) {
Integer caldata;
public String getCalendarData(String key) {
String caldata = "";
String cacheKey = CALENDAR_DATA + key;
removeEmptyReferences();
ResourceReference data = cache.get(cacheKey);
if (data == null || ((caldata = (Integer) data.get()) == null)) {
if (data == null || ((caldata = (String) data.get()) == null)) {
ResourceBundle rb = localeData.getCalendarData(locale);
if (rb.containsKey(key)) {
caldata = Integer.parseInt(rb.getString(key));
} else {
caldata = 0;
caldata = rb.getString(key);
}
cache.put(cacheKey,
new ResourceReference(cacheKey, (Object) caldata, referenceQueue));
new ResourceReference(cacheKey, caldata, referenceQueue));
}
return caldata;

View file

@ -1,5 +1,5 @@
/*
* Copyright (c) 1999, 2012, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 1999, 2017, Oracle and/or its affiliates. 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
@ -173,9 +173,14 @@ public class NumberFormatProviderImpl extends NumberFormatProvider implements Av
throw new NullPointerException();
}
// Check for region override
Locale override = locale.getUnicodeLocaleType("nu") == null ?
CalendarDataUtility.findRegionOverride(locale) :
locale;
LocaleProviderAdapter adapter = LocaleProviderAdapter.forType(type);
String[] numberPatterns = adapter.getLocaleResources(locale).getNumberPatterns();
DecimalFormatSymbols symbols = DecimalFormatSymbols.getInstance(locale);
String[] numberPatterns = adapter.getLocaleResources(override).getNumberPatterns();
DecimalFormatSymbols symbols = DecimalFormatSymbols.getInstance(override);
int entry = (choice == INTEGERSTYLE) ? NUMBERSTYLE : choice;
DecimalFormat format = new DecimalFormat(numberPatterns[entry], symbols);

View file

@ -1,5 +1,5 @@
/*
* Copyright (c) 2012, 2015, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2012, 2017, Oracle and/or its affiliates. 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
@ -160,28 +160,24 @@ public class SPILocaleProviderAdapter extends AuxLocaleProviderAdapter {
@Override
public BreakIterator getWordInstance(Locale locale) {
BreakIteratorProvider bip = getImpl(locale);
assert bip != null;
return bip.getWordInstance(locale);
}
@Override
public BreakIterator getLineInstance(Locale locale) {
BreakIteratorProvider bip = getImpl(locale);
assert bip != null;
return bip.getLineInstance(locale);
}
@Override
public BreakIterator getCharacterInstance(Locale locale) {
BreakIteratorProvider bip = getImpl(locale);
assert bip != null;
return bip.getCharacterInstance(locale);
}
@Override
public BreakIterator getSentenceInstance(Locale locale) {
BreakIteratorProvider bip = getImpl(locale);
assert bip != null;
return bip.getSentenceInstance(locale);
}
@ -215,7 +211,6 @@ public class SPILocaleProviderAdapter extends AuxLocaleProviderAdapter {
@Override
public Collator getInstance(Locale locale) {
CollatorProvider cp = getImpl(locale);
assert cp != null;
return cp.getInstance(locale);
}
}
@ -249,21 +244,18 @@ public class SPILocaleProviderAdapter extends AuxLocaleProviderAdapter {
@Override
public DateFormat getTimeInstance(int style, Locale locale) {
DateFormatProvider dfp = getImpl(locale);
assert dfp != null;
return dfp.getTimeInstance(style, locale);
}
@Override
public DateFormat getDateInstance(int style, Locale locale) {
DateFormatProvider dfp = getImpl(locale);
assert dfp != null;
return dfp.getDateInstance(style, locale);
}
@Override
public DateFormat getDateTimeInstance(int dateStyle, int timeStyle, Locale locale) {
DateFormatProvider dfp = getImpl(locale);
assert dfp != null;
return dfp.getDateTimeInstance(dateStyle, timeStyle, locale);
}
}
@ -297,7 +289,6 @@ public class SPILocaleProviderAdapter extends AuxLocaleProviderAdapter {
@Override
public DateFormatSymbols getInstance(Locale locale) {
DateFormatSymbolsProvider dfsp = getImpl(locale);
assert dfsp != null;
return dfsp.getInstance(locale);
}
}
@ -331,7 +322,6 @@ public class SPILocaleProviderAdapter extends AuxLocaleProviderAdapter {
@Override
public DecimalFormatSymbols getInstance(Locale locale) {
DecimalFormatSymbolsProvider dfsp = getImpl(locale);
assert dfsp != null;
return dfsp.getInstance(locale);
}
}
@ -365,28 +355,24 @@ public class SPILocaleProviderAdapter extends AuxLocaleProviderAdapter {
@Override
public NumberFormat getCurrencyInstance(Locale locale) {
NumberFormatProvider nfp = getImpl(locale);
assert nfp != null;
return nfp.getCurrencyInstance(locale);
}
@Override
public NumberFormat getIntegerInstance(Locale locale) {
NumberFormatProvider nfp = getImpl(locale);
assert nfp != null;
return nfp.getIntegerInstance(locale);
}
@Override
public NumberFormat getNumberInstance(Locale locale) {
NumberFormatProvider nfp = getImpl(locale);
assert nfp != null;
return nfp.getNumberInstance(locale);
}
@Override
public NumberFormat getPercentInstance(Locale locale) {
NumberFormatProvider nfp = getImpl(locale);
assert nfp != null;
return nfp.getPercentInstance(locale);
}
}
@ -420,14 +406,12 @@ public class SPILocaleProviderAdapter extends AuxLocaleProviderAdapter {
@Override
public int getFirstDayOfWeek(Locale locale) {
CalendarDataProvider cdp = getImpl(locale);
assert cdp != null;
return cdp.getFirstDayOfWeek(locale);
}
@Override
public int getMinimalDaysInFirstWeek(Locale locale) {
CalendarDataProvider cdp = getImpl(locale);
assert cdp != null;
return cdp.getMinimalDaysInFirstWeek(locale);
}
}
@ -463,7 +447,6 @@ public class SPILocaleProviderAdapter extends AuxLocaleProviderAdapter {
int field, int value,
int style, Locale locale) {
CalendarNameProvider cdp = getImpl(locale);
assert cdp != null;
return cdp.getDisplayName(calendarType, field, value, style, locale);
}
@ -472,7 +455,6 @@ public class SPILocaleProviderAdapter extends AuxLocaleProviderAdapter {
int field, int style,
Locale locale) {
CalendarNameProvider cdp = getImpl(locale);
assert cdp != null;
return cdp.getDisplayNames(calendarType, field, style, locale);
}
}
@ -506,14 +488,12 @@ public class SPILocaleProviderAdapter extends AuxLocaleProviderAdapter {
@Override
public String getSymbol(String currencyCode, Locale locale) {
CurrencyNameProvider cnp = getImpl(locale);
assert cnp != null;
return cnp.getSymbol(currencyCode, locale);
}
@Override
public String getDisplayName(String currencyCode, Locale locale) {
CurrencyNameProvider cnp = getImpl(locale);
assert cnp != null;
return cnp.getDisplayName(currencyCode, locale);
}
}
@ -547,30 +527,38 @@ public class SPILocaleProviderAdapter extends AuxLocaleProviderAdapter {
@Override
public String getDisplayLanguage(String languageCode, Locale locale) {
LocaleNameProvider lnp = getImpl(locale);
assert lnp != null;
return lnp.getDisplayLanguage(languageCode, locale);
}
@Override
public String getDisplayScript(String scriptCode, Locale locale) {
LocaleNameProvider lnp = getImpl(locale);
assert lnp != null;
return lnp.getDisplayScript(scriptCode, locale);
}
@Override
public String getDisplayCountry(String countryCode, Locale locale) {
LocaleNameProvider lnp = getImpl(locale);
assert lnp != null;
return lnp.getDisplayCountry(countryCode, locale);
}
@Override
public String getDisplayVariant(String variant, Locale locale) {
LocaleNameProvider lnp = getImpl(locale);
assert lnp != null;
return lnp.getDisplayVariant(variant, locale);
}
@Override
public String getDisplayUnicodeExtensionKey(String key, Locale locale) {
LocaleNameProvider lnp = getImpl(locale);
return lnp.getDisplayUnicodeExtensionKey(key, locale);
}
@Override
public String getDisplayUnicodeExtensionType(String extType, String key, Locale locale) {
LocaleNameProvider lnp = getImpl(locale);
return lnp.getDisplayUnicodeExtensionType(extType, key, locale);
}
}
static class TimeZoneNameProviderDelegate extends TimeZoneNameProvider
@ -602,14 +590,12 @@ public class SPILocaleProviderAdapter extends AuxLocaleProviderAdapter {
@Override
public String getDisplayName(String ID, boolean daylight, int style, Locale locale) {
TimeZoneNameProvider tznp = getImpl(locale);
assert tznp != null;
return tznp.getDisplayName(ID, daylight, style, locale);
}
@Override
public String getGenericDisplayName(String ID, int style, Locale locale) {
TimeZoneNameProvider tznp = getImpl(locale);
assert tznp != null;
return tznp.getGenericDisplayName(ID, style, locale);
}
}

View file

@ -1,5 +1,5 @@
/*
* Copyright (c) 2005, 2015, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2005, 2017, Oracle and/or its affiliates. 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
@ -31,10 +31,13 @@ import java.util.List;
import java.util.Locale;
import java.util.Map;
import java.util.Objects;
import java.util.Optional;
import java.util.Set;
import java.util.concurrent.ConcurrentHashMap;
import java.util.spi.TimeZoneNameProvider;
import sun.util.calendar.ZoneInfo;
import sun.util.cldr.CLDRLocaleProviderAdapter;
import static sun.util.locale.provider.LocaleProviderAdapter.Type;
/**
* Utility class that deals with the localized time zone names
@ -152,6 +155,18 @@ public final class TimeZoneNameUtility {
}
}
/**
* Converts the time zone id from LDML's 5-letter id to tzdb's id
*
* @param shortID time zone short ID defined in LDML
* @return the tzdb's time zone ID
*/
public static Optional<String> convertLDMLShortID(String shortID) {
return ((CLDRLocaleProviderAdapter)LocaleProviderAdapter.forType(Type.CLDR))
.getTimeZoneID(shortID)
.map(id -> id.replaceAll("\\s.*", ""));
}
private static String[] retrieveDisplayNamesImpl(String id, Locale locale) {
LocaleServiceProviderPool pool =
LocaleServiceProviderPool.getPool(TimeZoneNameProvider.class);

View file

@ -1,5 +1,5 @@
#
# Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
# Copyright (c) 2005, 2017, Oracle and/or its affiliates. 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
@ -1164,8 +1164,7 @@ ZW=Zimbabwe
# locale name patterns
# rarely localized
DisplayNamePattern={0,choice,0#|1#{1}|2#{1} ({2})}
ListPattern={0,choice,0#|1#{1}|2#{1},{2}|3#{1},{2},{3}}
ListKeyTypePattern={0}:{1}
ListCompositionPattern={0},{1}