1 package org.unicode.cldr.tool; 2 3 import com.ibm.icu.impl.Relation; 4 import com.ibm.icu.lang.UCharacter; 5 import com.ibm.icu.text.Collator; 6 import com.ibm.icu.text.DateFormatSymbols; 7 import com.ibm.icu.text.UnicodeSet; 8 import com.ibm.icu.util.ULocale; 9 import java.io.File; 10 import java.io.IOException; 11 import java.io.PrintWriter; 12 import java.util.Locale; 13 import java.util.Map; 14 import java.util.Set; 15 import java.util.TreeMap; 16 import java.util.TreeSet; 17 import java.util.regex.Matcher; 18 import org.unicode.cldr.draft.FileUtilities; 19 import org.unicode.cldr.util.CLDRFile; 20 import org.unicode.cldr.util.CLDRFile.WinningChoice; 21 import org.unicode.cldr.util.CLDRPaths; 22 import org.unicode.cldr.util.CldrUtility; 23 import org.unicode.cldr.util.Factory; 24 import org.unicode.cldr.util.Pair; 25 import org.unicode.cldr.util.PathUtilities; 26 import org.unicode.cldr.util.PatternCache; 27 import org.unicode.cldr.util.SimpleFactory; 28 import org.unicode.cldr.util.StandardCodes; 29 import org.unicode.cldr.util.TransliteratorUtilities; 30 import org.unicode.cldr.util.XMLFileReader; 31 32 class ExtractMessages { 33 public static final UnicodeSet LATIN_SCRIPT = new UnicodeSet("[:script=latin:]").freeze(); 34 35 private static Matcher fileMatcher; 36 37 public static PrintWriter output; 38 39 public static boolean SKIPEQUALS = true; 40 public static boolean SKIPIFCLDR = true; 41 public static String DIR = CLDRPaths.GEN_DIRECTORY + "/../additions/"; 42 main(String[] args)43 public static void main(String[] args) throws IOException { 44 double startTime = System.currentTimeMillis(); 45 output = FileUtilities.openUTF8Writer(DIR, "additions.txt"); 46 int totalCount = 0; 47 Set<String> skipped = new TreeSet<>(); 48 49 try { 50 String sourceDirectory = getProperty("SOURCE", null); 51 if (sourceDirectory == null) { 52 System.out.println("Need Source Directory! "); 53 return; 54 } 55 fileMatcher = PatternCache.get(getProperty("FILE", ".*")).matcher(""); 56 57 SKIPIFCLDR = getProperty("SKIPIFCLDR", null) != null; 58 59 boolean showMissing = true; 60 61 File src = new File(sourceDirectory); 62 63 XMLFileReader xfr = new XMLFileReader().setHandler(new EnglishHandler()); 64 xfr.read( 65 src + "/en.xmb", 66 XMLFileReader.CONTENT_HANDLER | XMLFileReader.ERROR_HANDLER, 67 false); 68 69 for (File file : src.listFiles()) { 70 if (file.isDirectory()) continue; 71 if (file.length() == 0) continue; 72 String canonicalFile = PathUtilities.getNormalizedPathString(file); 73 if (!canonicalFile.endsWith(".xtb")) { 74 continue; 75 } 76 77 String name = file.getName(); 78 name = name.substring(0, name.length() - 4); 79 80 if (!fileMatcher.reset(name).matches()) { 81 continue; 82 } 83 System.out.println("* " + canonicalFile); 84 85 try { 86 otherHandler.setLocale(name); 87 } catch (RuntimeException e1) { 88 System.out.println( 89 "Skipping, no CLDR locale file: " 90 + name 91 + "\t" 92 + english.getName(name) 93 + "\t" 94 + e1.getClass().getName() 95 + "\t" 96 + e1.getMessage()); 97 skipped.add(name); 98 continue; 99 } 100 101 xfr = new XMLFileReader().setHandler(otherHandler); 102 try { 103 xfr.read( 104 canonicalFile, 105 XMLFileReader.CONTENT_HANDLER | XMLFileReader.ERROR_HANDLER, 106 false); 107 } catch (RuntimeException e) { 108 System.out.println(e.getMessage()); 109 continue; 110 } 111 112 // now write it out 113 CLDRFile newFile = SimpleFactory.makeFile(otherHandler.getLocale()); 114 int itemCount = 0; 115 for (DataHandler dataHandler : dataHandlers) { 116 if (showMissing) { 117 System.out.println("case " + dataHandler.type + ":"); 118 for (String value : dataHandler.missing) { 119 System.out.println("addName(\"" + value + "\", \"XXX\", true);"); 120 } 121 } 122 123 for (String id : dataHandler.id_to_value.keySet()) { 124 Set<String> otherValue = dataHandler.id_to_value.getAll(id); 125 if (otherValue == null || otherValue.size() == 0) continue; 126 String cldrValue = dataHandler.id_to_cldrValue.get(id); 127 int count = 0; 128 for (String oValue : otherValue) { 129 itemCount++; 130 output.println( 131 otherHandler.getLocale() 132 + "\t" 133 + dataHandler.type 134 + "\t" 135 + id 136 + "\t" 137 + oValue 138 + (cldrValue == null ? "" : "\tcldr:\t" + cldrValue) 139 + (count == 0 140 ? "" 141 : "\talt:\t" + String.valueOf(count))); 142 newFile.add(dataHandler.getPath(id, count), oValue); 143 } 144 } 145 } 146 PrintWriter cldrOut = 147 FileUtilities.openUTF8Writer(DIR, otherHandler.getLocale() + ".xml"); 148 newFile.write(cldrOut); 149 cldrOut.close(); 150 151 output.println(); 152 showMissing = false; 153 output.flush(); 154 System.out.println("\titems: " + itemCount); 155 totalCount += itemCount; 156 } 157 158 for (String name : skipped) { 159 System.out.println( 160 "\tSkipping, no CLDR locale file: " + name + "\t" + english.getName(name)); 161 } 162 double deltaTime = System.currentTimeMillis() - startTime; 163 System.out.println("Elapsed: " + deltaTime / 1000.0 + " seconds"); 164 System.out.println("\ttotal items: " + totalCount); 165 } finally { 166 output.close(); 167 } 168 } 169 getProperty(String key, String defaultValue)170 private static String getProperty(String key, String defaultValue) { 171 String fileRegex = System.getProperty(key); 172 if (fileRegex == null) fileRegex = defaultValue; 173 System.out.println("-D" + key + "=" + fileRegex); 174 return fileRegex; 175 } 176 177 private static Map<String, Pair<String, DataHandler>> numericId_Id = new TreeMap<>(); 178 private static Matcher numericIdMatcher = 179 PatternCache.get("\\[@id=\"([^\"]+)\"\\]").matcher(""); 180 private static Factory cldrFactory = Factory.make(CLDRPaths.MAIN_DIRECTORY, ".*"); 181 private static CLDRFile english = cldrFactory.make("en", true); 182 183 private static class EnglishHandler extends XMLFileReader.SimpleHandler { 184 185 @Override handlePathValue(String path, String value)186 public void handlePathValue(String path, String value) { 187 for (DataHandler handler : dataHandlers) { 188 if (handler.matches(path)) { 189 // //messagebundle/msg[@id="1907015897505457162"][@seq="71982"][@desc="Andorra 190 // is a display name for a timezone"][@xml:space="default"] 191 numericIdMatcher.reset(path).find(); 192 String id = numericIdMatcher.group(1); 193 value = value.trim(); 194 if (value.length() == 0) return; // skip empties 195 value = TransliteratorUtilities.fromXML.transliterate(value); 196 String realID = handler.getCode(value); 197 if (realID == null) { 198 handler.missing.add(value); 199 return; 200 } 201 numericId_Id.put(id, new Pair<>(realID, handler)); 202 // System.out.println(id + "\t" + path + "\t" + value); 203 } 204 } 205 } 206 } 207 208 public static Collator col = Collator.getInstance(ULocale.ENGLISH); 209 210 static { 211 col.setStrength(Collator.SECONDARY); 212 } 213 214 private static OtherHandler otherHandler = new OtherHandler(); 215 216 private static class OtherHandler extends XMLFileReader.SimpleHandler { 217 private String locale; 218 private ULocale uLocale; 219 CLDRFile cldrFile; 220 boolean usesLatin; 221 222 @Override handlePathValue(String path, String value)223 public void handlePathValue(String path, String value) { 224 // //messagebundle/msg[@id="1907015897505457162"][@seq="71982"][@desc="Andorra is a 225 // display name for a timezone"][@xml:space="default"] 226 value = value.trim(); 227 if (value.length() == 0) return; // skip empties 228 229 numericIdMatcher.reset(path).find(); 230 String numericId = numericIdMatcher.group(1); 231 Pair<String, DataHandler> id_handler = numericId_Id.get(numericId); 232 if (id_handler == null) return; 233 String id = id_handler.getFirst(); 234 DataHandler dataHandler = id_handler.getSecond(); 235 236 if (!usesLatin && LATIN_SCRIPT.containsSome(value)) { 237 // output.println(locale + "\tSkipping item with latin characters\t" + id + "\t" + 238 // value); 239 return; 240 } 241 242 // this should be reorganized to put more in the DataHandler, but for now... 243 244 value = dataHandler.fixValue(uLocale, value); 245 246 String cldrValue = dataHandler.getCldrValue(cldrFile, id); 247 if (cldrValue != null) { 248 if (col.compare(cldrValue, value) == 0) { 249 // System.out.println("Duplicate for " + id + "\t" + value); 250 if (SKIPEQUALS) return; 251 } else { 252 if (SKIPIFCLDR) return; 253 // output.println(locale + "\tDifferent value for\t" + id + "\t" + value + 254 // "\tcldr:\t" + cldrValue); 255 } 256 } 257 dataHandler.addValues(id, value, cldrValue); 258 } 259 setLocale(String locale)260 public void setLocale(String locale) { 261 262 // skip en, fr_CA 263 // as, sa bad 264 // ku cldr-latin, g-arabic 265 // ml, my, pa, te has mixed english 266 // TODO move this into datahandler eventually 267 locale = fixLocale(locale); 268 this.locale = locale; 269 this.uLocale = new ULocale(locale); 270 String lang = uLocale.getLanguage(); 271 if (locale.equals("fr_CA") || lang.equals("en")) { 272 throw new RuntimeException("Skipping " + locale); 273 } 274 cldrFile = cldrFactory.make(locale, false); 275 UnicodeSet exemplars = cldrFile.getExemplarSet("", WinningChoice.WINNING); 276 usesLatin = exemplars != null && exemplars.containsSome(LATIN_SCRIPT); 277 for (DataHandler dataHandler : dataHandlers) { 278 dataHandler.reset(cldrFile); 279 } 280 } 281 getLocale()282 public String getLocale() { 283 return locale; 284 } 285 } 286 287 static Map<String, String> fixLocaleMap = 288 CldrUtility.asMap( 289 new String[][] { 290 {"zh_CN", "zh"}, 291 {"zh_TW", "zh_Hant"}, 292 {"pt_BR", "pt"}, 293 {"in", "id"}, 294 {"iw", "he"}, 295 {"jw", "jv"}, 296 {"ku", "ku_Arab"}, 297 }); 298 fixLocale(String locale)299 private static String fixLocale(String locale) { 300 locale = locale.replace('-', '_'); 301 String newLocale = fixLocaleMap.get(locale); 302 if (newLocale != null) { 303 locale = newLocale; 304 } 305 return locale; 306 } 307 308 /* 309 * Language 310 * -DXMLPATH=".*form of language.*" 311 * 312 * Country 313 * -DXMLPATH=".*the country or region.*" 314 * 315 * Currency 316 * -DXMLPATH=".*currency name.*" 317 * 318 * Month Long/Short 319 * -DXMLPATH=".*Name of the month of .*" 320 * -DXMLPATH=".*3 letter abbreviation for name of Month.*" 321 * 322 * Week Long/Short 323 * -DXMLPATH=".*day in week.*" 324 * -DXMLPATH=".*Short Version of .*" 325 * 326 * Timezone 327 * DXMLPATH=".*is a display name for a timezone.*" 328 */ 329 330 enum Type { 331 LANGUAGE, 332 REGION, 333 CURRENCY, 334 MONTH, 335 MONTHSHORT, 336 DAY, 337 DAYSHORT, 338 TIMEZONE 339 } 340 341 static StandardCodes sc = StandardCodes.make(); 342 static DateFormatSymbols dfs = new DateFormatSymbols(ULocale.ENGLISH); 343 344 static DataHandler[] dataHandlers = { 345 new DataHandler(Type.LANGUAGE, ".*form of language.*"), 346 new DataHandler(Type.REGION, ".*the country or region.*"), 347 new DataHandler(Type.CURRENCY, ".*currency name.*"), 348 new DataHandler(Type.MONTH, ".*Name of the month of .*"), 349 new DataHandler(Type.MONTHSHORT, ".*3 letter abbreviation for name of Month.*"), 350 new DataHandler(Type.DAY, ".*day in week.*"), 351 new DataHandler(Type.DAYSHORT, ".*Short Version of .*"), 352 new DataHandler(Type.TIMEZONE, ".*is a display name for a timezone.*"), 353 }; 354 355 enum CasingAction { 356 NONE, 357 FORCE_TITLE, 358 FORCE_LOWER 359 } 360 361 static class DataHandler implements Comparable<DataHandler> { 362 // mostly stable 363 private Matcher matcher; 364 private Type type; 365 private Map<String, String> name_code = new TreeMap<>(); 366 // private Map<String,String> code_name = new TreeMap(); 367 private Set<String> missing = new TreeSet<>(); 368 369 // changes with each locale, must call reset 370 private Relation<String, String> id_to_value = 371 Relation.of(new TreeMap<String, Set<String>>(), TreeSet.class); 372 private Map<String, String> id_to_cldrValue = new TreeMap<>(); 373 private CasingAction forceCasing = CasingAction.NONE; 374 reset(CLDRFile cldrFile)375 public void reset(CLDRFile cldrFile) { 376 id_to_value.clear(); 377 id_to_cldrValue.clear(); 378 forceCasing = CasingAction.NONE; 379 String key = null; 380 switch (type) { 381 case LANGUAGE: 382 key = "en"; 383 break; 384 case REGION: 385 key = "FR"; 386 break; 387 case CURRENCY: 388 key = "GBP"; 389 break; 390 case MONTH: 391 case MONTHSHORT: 392 key = "1"; 393 break; 394 case DAY: 395 case DAYSHORT: 396 key = "mon"; 397 break; 398 case TIMEZONE: 399 key = "America/New_York"; 400 break; 401 } 402 String sample = getCldrValue(cldrFile, key); 403 if (sample != null) { 404 if (UCharacter.isLowerCase(sample.charAt(0))) { 405 forceCasing = CasingAction.FORCE_LOWER; 406 } else if (UCharacter.isUpperCase(sample.charAt(0))) { 407 forceCasing = CasingAction.FORCE_TITLE; 408 } 409 } 410 } 411 fixValue(ULocale uLocale, String value)412 public String fixValue(ULocale uLocale, String value) { 413 value = TransliteratorUtilities.fromXML.transliterate(value); 414 415 if (forceCasing == CasingAction.FORCE_LOWER) { 416 if (!UCharacter.isLowerCase(value.charAt(0))) { 417 value = UCharacter.toLowerCase(value); 418 } 419 } else if (forceCasing == CasingAction.FORCE_TITLE) { 420 if (!UCharacter.isUpperCase(value.charAt(0))) { 421 value = UCharacter.toTitleCase(uLocale, value, null); 422 } 423 } 424 425 return value; 426 } 427 addValues(String id, String value, String cldrValue)428 public void addValues(String id, String value, String cldrValue) { 429 id_to_value.put(id, value); 430 if (cldrValue != null) { 431 id_to_cldrValue.put(id, cldrValue); 432 } 433 } 434 addName(String name, String code, boolean skipMessage)435 public void addName(String name, String code, boolean skipMessage) { 436 // String old = code_name.get(code); 437 // if (old != null) { 438 // if (!skipMessage) { 439 // System.out.println("Name collision:\t" + code + "\tnew: " + name + "\tkeeping: " + 440 // old); 441 // } 442 // } else { 443 // } 444 // code_name.put(code, name); 445 name_code.put(name, code); 446 } 447 DataHandler(Type type, String pattern)448 DataHandler(Type type, String pattern) { 449 this.type = type; 450 matcher = PatternCache.get(pattern).matcher(""); 451 switch (type) { 452 case LANGUAGE: 453 for (String code : sc.getAvailableCodes("language")) { 454 String name = english.getName("language", code); 455 if (name == null) { 456 // System.out.println("Missing name for: " + code); 457 continue; 458 } 459 addName(name, code.replace("-", "_"), false); 460 } 461 // add irregular names 462 addName("English (US)", "en_US", true); 463 addName("English (UK)", "en_GB", true); 464 // addName("English (AU)", "en_AU/short"); 465 // addName("Portuguese (PT)", "pt_PT/short"); 466 // addName("Portuguese (BR)", "pt_BR/short"); 467 addName("Chinese (Simplified)", "zh_Hans", true); 468 addName("Chinese (Traditional)", "zh_Hant", true); 469 addName("Norwegian (Nynorsk)", "nn", true); 470 addName("Portuguese (Portugal)", "pt_PT", true); 471 addName("Portuguese (Brazil)", "pt_BR", true); 472 addName("English (Australia)", "en_AU", true); 473 addName("Scots Gaelic", "gd", true); 474 addName("Frisian", "fy", true); 475 addName("Sesotho", "st", true); 476 addName("Kyrgyz", "ky", true); 477 addName("Laothian", "lo", true); 478 addName("Cambodian", "km", true); 479 addName("Greenlandic", "kl", true); 480 addName("Inupiak", "ik", true); 481 addName("Volapuk", "vo", true); 482 addName("Byelorussian", "be", true); 483 addName("Faeroese", "fo", true); 484 addName("Singhalese", "si", true); 485 addName("Gaelic", "ga", true); // IRISH 486 addName("Bhutani", "dz", true); 487 addName("Setswana", "tn", true); 488 addName("Siswati", "ss", true); 489 addName("Sangro", "sg", true); 490 // addName("Kirundi", "XXX"); // no ISO2 code 491 // addName("Sudanese", "XXX"); // ??? 492 break; 493 case REGION: 494 for (String code : sc.getAvailableCodes("territory")) { 495 String name = english.getName("territory", code); 496 if (name == null) { 497 // System.out.println("Missing name for: " + code); 498 continue; 499 } 500 addName(name, code, false); 501 } 502 // add irregular names 503 addName("Bosnia and Herzegowina", "BA", true); 504 addName("Congo", "CG", true); 505 addName("Congo, Democratic Republic of the", "CD", true); 506 addName("Congo, The Democratic Republic of the", "CD", true); 507 addName("Cote D'ivoire", "CI", true); 508 addName("Côte d'Ivoire", "CI", true); 509 addName("Equitorial Guinea", "GQ", true); 510 addName("French Quiana", "GF", true); 511 addName("Heard and Mc Donald Islands", "HM", true); 512 addName("Holy See (Vatican City State)", "VA", true); 513 addName("Iran (Islamic Republic of)", "IR", true); 514 addName("Korea, Democratic People's Republic of", "KP", true); 515 addName("Korea, Republic of", "KR", true); 516 addName("Libyan Arab Jamahiriya", "LY", true); 517 addName("Lichtenstein", "LI", true); 518 addName("Macao", "MO", true); 519 addName("Micronesia, Federated States of", "FM", true); 520 addName("Palestine", "PS", true); 521 addName("Serbia and Montenegro", "CS", true); 522 addName("Slovakia (Slovak Republic)", "SK", true); 523 addName("São Tomé and Príncipe", "ST", true); 524 addName("The Former Yugoslav Republic of Macedonia", "MK", true); 525 addName("United States minor outlying islands", "UM", true); 526 addName("Vatican City", "VA", true); 527 addName("Virgin Islands, British", "VG", true); 528 addName("Virgin Islands, U.S.", "VI", true); 529 addName("Zaire", "CD", true); 530 addName("Åland Islands", "AX", true); 531 break; 532 case CURRENCY: 533 for (String code : sc.getAvailableCodes("currency")) { 534 String name = english.getName("currency", code); 535 if (name == null) { 536 // System.out.println("Missing name for: " + code); 537 continue; 538 } 539 addName(name, code, false); 540 } 541 // add irregular names 542 addName("Australian Dollars", "AUD", true); 543 addName("Bolivian Boliviano", "BOB", true); 544 addName("British Pounds Sterling", "GBP", true); 545 addName("Bulgarian Lev", "BGN", true); 546 addName("Canadian Dollars", "CAD", true); 547 addName("Czech Koruna", "CZK", true); 548 addName("Danish Kroner", "DKK", true); 549 addName("Denmark Kroner", "DKK", true); 550 addName("Deutsche Marks", "DEM", true); 551 addName("Euros", "EUR", true); 552 addName("French Franks", "FRF", true); 553 addName("Hong Kong Dollars", "HKD", true); 554 addName("Israeli Shekel", "ILS", true); 555 addName("Lithuanian Litas", "LTL", true); 556 addName("Mexico Peso", "MXN", true); 557 addName("New Romanian Leu", "RON", true); 558 addName("New Taiwan Dollar", "TWD", true); 559 addName("New Zealand Dollars", "NZD", true); 560 addName("Norway Kroner", "NOK", true); 561 addName("Norwegian Kroner", "NOK", true); 562 addName("Peruvian Nuevo Sol", "PEN", true); 563 addName("Polish New Zloty", "PLN", true); 564 addName("Polish NewZloty", "PLN", true); 565 addName("Russian Rouble", "RUB", true); 566 addName("Singapore Dollars", "SGD", true); 567 addName("Slovenian Tolar", "SIT", true); 568 addName("Sweden Kronor", "SEK", true); 569 addName("Swedish Kronor", "SEK", true); 570 addName("Swiss Francs", "CHF", true); 571 addName("US Dollars", "USD", true); 572 addName("United Arab EmiratesD irham", "AED", true); 573 addName("Venezuela Bolivar", "VEB", true); 574 addName("Yuan Renminbi", "CNY", true); 575 break; 576 case TIMEZONE: 577 for (String code : sc.getAvailableCodes("tzid")) { 578 String[] parts = code.split("/"); 579 addName(parts[parts.length - 1].replace("_", " "), code, false); 580 } 581 // add irregular names 582 addName("Alaska Time", "America/Anchorage", true); 583 // addName("Atlantic Time", "XXX", true); 584 // addName("Atlantic Time - Halifax", "America/Halifax", true); 585 addName("Canary Islands", "Atlantic/Canary", true); 586 // addName("Central European Time", "XXX", true); 587 // addName("Central European Time - Madrid", "Europe/Madrid", true); 588 // addName("Central Time", "America/Chicago", true); 589 // addName("Central Time - Adelaide", "Australia/Adelaide", true); 590 // addName("Central Time - Darwin", "Australia/Darwin", true); 591 // addName("Central Time - Mexico City", "America/Mexico_City", true); 592 // addName("Central Time - Mexico City, Monterrey", "America/Monterrey", true); 593 // addName("Central Time - Regina", "America/Regina", true); 594 // addName("Central Time - Sasketchewan", "XXX", true); 595 // addName("Central Time - Winnipeg", "America/Winnipeg", true); 596 // addName("China Time - Beijing", "XXX", true); 597 addName("Dumont D'Urville", "Antarctica/DumontDUrville", true); 598 addName("Easter Island", "Pacific/Easter", true); 599 // addName("Eastern European Time", "XXX", true); 600 // addName("Eastern Standard Time", "XXX", true); 601 // addName("Eastern Time", "XXX", true); 602 // addName("Eastern Time - Brisbane", "Australia/Brisbane", true); 603 // addName("Eastern Time - Hobart", "Australia/Hobart", true); 604 // addName("Eastern Time - Iqaluit", "America/Iqaluit", true); 605 // addName("Eastern Time - Melbourne, Sydney", "XXX", true); 606 // addName("Eastern Time - Montreal", "XXX", true); 607 // addName("Eastern Time - Toronto", "XXX", true); 608 // addName("GMT (no daylight saving)", "XXX", true); 609 // addName("Greenwich Mean Time", "XXX", true); 610 // addName("Hanoi", "XXX", true); 611 // addName("Hawaii Time", "XXX", true); 612 // addName("India Standard Time", "XXX", true); 613 // addName("International Date Line West", "XXX", true); 614 // addName("Japan Time", "XXX", true); 615 // addName("Moscow+00", "XXX", true); 616 // addName("Moscow+01 - Samara", "XXX", true); 617 // addName("Moscow+02 - Yekaterinburg", "XXX", true); 618 // addName("Moscow+03 - Omsk, Novosibirsk", "XXX", true); 619 // addName("Moscow+04 - Krasnoyarsk", "XXX", true); 620 // addName("Moscow+05 - Irkutsk", "XXX", true); 621 // addName("Moscow+06 - Yakutsk", "XXX", true); 622 // addName("Moscow+07 - Vladivostok, Sakhalin", "XXX", true); 623 // addName("Moscow+07 - Yuzhno-Sakhalinsk", "XXX", true); 624 // addName("Moscow+08 - Magadan", "XXX", true); 625 // addName("Moscow+09 - Kamchatka, Anadyr", "XXX", true); 626 // addName("Moscow+09 - Petropavlovsk-Kamchatskiy", "XXX", true); 627 // addName("Moscow-01 - Kaliningrad", "XXX", true); 628 // addName("Mountain Time", "XXX", true); 629 // addName("Mountain Time - Arizona", "XXX", true); 630 // addName("Mountain Time - Chihuahua, Mazatlan", "XXX", true); 631 // addName("Mountain Time - Dawson Creek", "XXX", true); 632 // addName("Mountain Time - Edmonton", "XXX", true); 633 // addName("Mountain Time - Hermosillo", "XXX", true); 634 // addName("Mountain Time - Yellowknife", "XXX", true); 635 // addName("Newfoundland Time - St. Johns", "XXX", true); 636 // addName("Pacific Time", "XXX", true); 637 // addName("Pacific Time - Tijuana", "XXX", true); 638 // addName("Pacific Time - Vancouver", "XXX", true); 639 // addName("Pacific Time - Whitehorse", "XXX", true); 640 addName("Salvador", "America/El_Salvador", true); 641 addName("St. Kitts", "America/St_Kitts", true); 642 addName("St. Lucia", "America/St_Lucia", true); 643 addName("St. Thomas", "America/St_Thomas", true); 644 addName("St. Vincent", "America/St_Vincent", true); 645 // addName("Tel Aviv", "XXX", true); 646 // addName("Western European Time", "XXX", true); 647 // addName("Western European Time - Canary Islands", "XXX", true); 648 // addName("Western European Time - Ceuta", "XXX", true); 649 // addName("Western Time - Perth", "XXX", true); 650 break; 651 case MONTH: 652 case MONTHSHORT: 653 String[] names = type == Type.MONTH ? dfs.getMonths() : dfs.getShortMonths(); 654 for (int i = 0; i < names.length; ++i) { 655 addName(names[i], String.valueOf(i + 1), true); 656 } 657 break; 658 case DAY: 659 case DAYSHORT: 660 String[] names2 = type == Type.DAY ? dfs.getWeekdays() : dfs.getShortWeekdays(); 661 for (int i = 1; i < names2.length; ++i) { 662 addName( 663 names2[i], 664 names2[i].substring(0, 3).toLowerCase(Locale.ENGLISH), 665 true); 666 } 667 break; 668 default: 669 // throw new IllegalArgumentException(); 670 break; 671 } 672 } 673 getCldrValue(CLDRFile cldrFile, String id)674 public String getCldrValue(CLDRFile cldrFile, String id) { 675 String result = cldrFile.getStringValue(getPath(id)); 676 // cldrFile.getName(CLDRFile.LANGUAGE_NAME, id, false); 677 if (result == null && type == Type.TIMEZONE) { 678 String[] parts = id.split("/"); 679 result = parts[parts.length - 1].replace("_", " "); 680 } 681 return result; 682 } 683 matches(String text)684 boolean matches(String text) { 685 return matcher.reset(text).matches(); 686 } 687 getCode(String value)688 String getCode(String value) { 689 return name_code.get(value); 690 } 691 692 @Override compareTo(DataHandler o)693 public int compareTo(DataHandler o) { 694 throw new IllegalArgumentException(); 695 } 696 getPath(String id, int count)697 String getPath(String id, int count) { 698 String result = getPath(id); 699 count += 650; 700 result += "[@alt=\"proposed-x" + count + "\"]"; 701 result += "[@draft=\"provisional\"]"; 702 return result; 703 } 704 getPath(String id)705 String getPath(String id) { 706 switch (type) { 707 case LANGUAGE: 708 return CLDRFile.getKey(CLDRFile.LANGUAGE_NAME, id); 709 case REGION: 710 return CLDRFile.getKey(CLDRFile.TERRITORY_NAME, id); 711 case CURRENCY: 712 return CLDRFile.getKey(CLDRFile.CURRENCY_NAME, id); 713 case TIMEZONE: 714 return "//ldml/dates/timeZoneNames/zone[@type=\"$1\"]/exemplarCity" 715 .replace("$1", id); 716 case MONTH: 717 return "//ldml/dates/calendars/calendar[@type=\"gregorian\"]/months/monthContext[@type=\"format\"]/monthWidth[@type=\"wide\"]/month[@type=\"$1\"]" 718 .replace("$1", id); 719 case MONTHSHORT: 720 return "//ldml/dates/calendars/calendar[@type=\"gregorian\"]/months/monthContext[@type=\"format\"]/monthWidth[@type=\"abbreviated\"]/month[@type=\"$1\"]" 721 .replace("$1", id); 722 case DAY: 723 return "//ldml/dates/calendars/calendar[@type=\"gregorian\"]/days/dayContext[@type=\"format\"]/dayWidth[@type=\"wide\"]/day[@type=\"$1\"]" 724 .replace("$1", id); 725 case DAYSHORT: 726 return "//ldml/dates/calendars/calendar[@type=\"gregorian\"]/days/dayContext[@type=\"format\"]/dayWidth[@type=\"abbreviated\"]/day[@type=\"$1\"]" 727 .replace("$1", id); 728 } 729 return null; 730 // 731 } 732 } 733 } 734