xref: /aosp_15_r20/external/cldr/tools/cldr-code/src/main/java/org/unicode/cldr/test/EmojiSubdivisionNames.java (revision 912701f9769bb47905792267661f0baf2b85bed5)
1 package org.unicode.cldr.test;
2 
3 import com.google.common.collect.ImmutableMap;
4 import com.google.common.collect.ImmutableSet;
5 import com.google.common.collect.ImmutableSortedSet;
6 import com.ibm.icu.util.ULocale;
7 import java.io.File;
8 import java.util.Collections;
9 import java.util.HashSet;
10 import java.util.Map;
11 import java.util.Set;
12 import java.util.SortedSet;
13 import java.util.TreeMap;
14 import java.util.concurrent.ConcurrentHashMap;
15 import java.util.regex.Matcher;
16 import java.util.regex.Pattern;
17 import org.unicode.cldr.draft.FileUtilities;
18 import org.unicode.cldr.util.CLDRConfig;
19 import org.unicode.cldr.util.CLDRFile;
20 import org.unicode.cldr.util.CLDRPaths;
21 import org.unicode.cldr.util.EmojiConstants;
22 import org.unicode.cldr.util.LanguageGroup;
23 import org.unicode.cldr.util.LocaleIDParser;
24 import org.unicode.cldr.util.Organization;
25 import org.unicode.cldr.util.StandardCodes;
26 
27 public class EmojiSubdivisionNames {
28     private static final String subdivisionPathPrefix =
29             "//ldml/localeDisplayNames/subdivisions/subdivision[@type=\"";
30     private static final String subdivisionPathSuffix = "\"]";
31     private static final Map<String, Map<String, String>> localeToNameToSubdivisionId =
32             new ConcurrentHashMap<>();
33     private static final Map<String, Map<String, String>> localeToSubdivisionIdToName =
34             new ConcurrentHashMap<>();
35 
36     private static final Pattern SUBDIVISION_PATTERN =
37             Pattern.compile(
38                     "\\s*<subdivision\\s+type=\"(gb(?:eng|sct|wls))\">([^<]+)</subdivision>");
39     private static final SortedSet<String> SUBDIVISION_FILE_NAMES =
40             ImmutableSortedSet.copyOf(new File(CLDRPaths.SUBDIVISIONS_DIRECTORY).list());
41 
42     static {
43         localeToNameToSubdivisionId.put("root", Collections.emptyMap());
44     }
45 
getSubdivisionIdToName(String localeID)46     public static Map<String, String> getSubdivisionIdToName(String localeID) {
47         Map<String, String> result = localeToSubdivisionIdToName.get(localeID);
48         if (result == null) {
49             load(localeID);
50             result = localeToSubdivisionIdToName.get(localeID);
51             if (result == null) {
52                 result = Collections.emptyMap();
53             }
54         }
55         return result;
56     }
57 
getNameToSubdivisionPath(String localeID)58     public static Map<String, String> getNameToSubdivisionPath(String localeID) {
59         Map<String, String> result = localeToNameToSubdivisionId.get(localeID);
60         if (result == null) {
61             load(localeID);
62             result = localeToNameToSubdivisionId.get(localeID);
63             if (result == null) {
64                 result = Collections.emptyMap();
65             }
66         }
67         return result;
68     }
69 
load(String localeID)70     private static void load(String localeID) {
71         try {
72             Map<String, String> _subdivisionIdToName;
73             Map<String, String> _nameToSubdivisionId;
74 
75             String fileName = localeID + ".xml";
76             if (SUBDIVISION_FILE_NAMES.contains(fileName)) {
77                 _nameToSubdivisionId = new TreeMap<>();
78                 _subdivisionIdToName = new TreeMap<>();
79                 Matcher m = SUBDIVISION_PATTERN.matcher("");
80                 for (String line :
81                         FileUtilities.in(new File(CLDRPaths.SUBDIVISIONS_DIRECTORY, fileName))) {
82                     if (m.reset(line).matches()) {
83                         String xpath =
84                                 subdivisionPathPrefix
85                                         + EmojiConstants.toTagSeq(m.group(1))
86                                         + subdivisionPathSuffix;
87                         _nameToSubdivisionId.put(m.group(2), xpath);
88                         _subdivisionIdToName.put(m.group(1), m.group(2));
89                     }
90                 }
91                 _nameToSubdivisionId =
92                         _nameToSubdivisionId.isEmpty()
93                                 ? Collections.emptyMap()
94                                 : ImmutableMap.copyOf(_nameToSubdivisionId);
95                 _subdivisionIdToName =
96                         _subdivisionIdToName.isEmpty()
97                                 ? Collections.emptyMap()
98                                 : ImmutableMap.copyOf(_subdivisionIdToName);
99             } else {
100                 String parentLocaleId = LocaleIDParser.getParent(localeID);
101                 _nameToSubdivisionId = getNameToSubdivisionPath(parentLocaleId);
102                 _subdivisionIdToName = localeToSubdivisionIdToName.get(parentLocaleId);
103             }
104             /*
105              * In practice _subdivisionIdToName == null actually happens here.
106              * Check for null rather than triggering NullPointerException.
107              */
108             if (_nameToSubdivisionId != null) {
109                 localeToNameToSubdivisionId.put(localeID, _nameToSubdivisionId);
110             }
111             if (_subdivisionIdToName != null) {
112                 localeToSubdivisionIdToName.put(localeID, _subdivisionIdToName);
113             }
114         } catch (Exception e) {
115             /*
116              * TODO: If there is a valid rationale for catching and ignoring all exceptions here,
117              * document it. Otherwise it should be avoided since it tends to hide programming errors.
118              */
119         }
120     }
121 
122     static Set<String> SUBDIVISIONS = ImmutableSet.of("gbeng", "gbsct", "gbwls");
123 
main(String[] args)124     public static void main(String[] args) {
125         System.out.print("Group\tOrd.\tLocale\tCode");
126         for (String sd : SUBDIVISIONS) {
127             System.out.print('\t');
128             System.out.print(sd);
129         }
130         System.out.println();
131         CLDRFile english = CLDRConfig.getInstance().getEnglish();
132         Set<String> locales = new HashSet<>();
133         for (String filename : SUBDIVISION_FILE_NAMES) {
134             if (filename.endsWith(".xml")) {
135                 String locale = filename.substring(0, filename.length() - 4);
136                 Map<String, String> map = getSubdivisionIdToName(locale);
137                 if (!map.isEmpty()) {
138                     locales.add(locale);
139                     ULocale ulocale = new ULocale(locale);
140                     LanguageGroup group = LanguageGroup.get(ulocale);
141                     int rank = LanguageGroup.rankInGroup(ulocale);
142                     System.out.print(
143                             group + "\t" + rank + "\t" + english.getName(locale) + "\t" + locale);
144                     for (String sd : SUBDIVISIONS) {
145                         System.out.print('\t');
146                         System.out.print(map.get(sd));
147                     }
148                     System.out.println();
149                 }
150             }
151         }
152         for (String locale : StandardCodes.make().getLocaleCoverageLocales(Organization.cldr)) {
153             if (locales.contains(locale)) {
154                 continue;
155             }
156             ULocale ulocale = new ULocale(locale);
157             String region = ulocale.getCountry();
158             if (!region.isEmpty() && !region.equals("PT") && !region.equals("GB")) {
159                 continue;
160             }
161             LanguageGroup group = LanguageGroup.get(ulocale);
162             int rank = LanguageGroup.rankInGroup(ulocale);
163             System.out.println(
164                     group + "\t" + rank + "\t" + english.getName(locale) + "\t" + locale);
165         }
166 
167         //        System.out.println(getSubdivisionIdToName("fr"));
168         //        System.out.println(getNameToSubdivisionPath("fr"));
169     }
170 }
171