1/* 2 * Copyright (c) 1998, 2016, Oracle and/or its affiliates. All rights reserved. 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * This code is free software; you can redistribute it and/or modify it 6 * under the terms of the GNU General Public License version 2 only, as 7 * published by the Free Software Foundation. 8 * 9 * This code is distributed in the hope that it will be useful, but WITHOUT 10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 12 * version 2 for more details (a copy is included in the LICENSE file that 13 * accompanied this code). 14 * 15 * You should have received a copy of the GNU General Public License version 16 * 2 along with this work; if not, write to the Free Software Foundation, 17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 18 * 19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 20 * or visit www.oracle.com if you need additional information or have any 21 * questions. 22 */ 23 24/* 25 * @test 26 * @summary test International Date Format 27 * @bug 8008577 28 * @library /java/text/testlib 29 * @run main/othervm -Djava.locale.providers=COMPAT,SPI IntlTestDateFormat 30 * @key randomness 31 */ 32/* 33(C) Copyright Taligent, Inc. 1996, 1997 - All Rights Reserved 34(C) Copyright IBM Corp. 1996, 1997 - All Rights Reserved 35 36 The original version of this source code and documentation is copyrighted and 37owned by Taligent, Inc., a wholly-owned subsidiary of IBM. These materials are 38provided under terms of a License Agreement between Taligent and Sun. This 39technology is protected by multiple US and International patents. This notice and 40attribution to Taligent may not be removed. 41 Taligent is a registered trademark of Taligent, Inc. 42*/ 43 44import java.text.*; 45import java.util.*; 46 47public class IntlTestDateFormat extends IntlTest { 48 // Values in milliseconds (== Date) 49 private static final long ONESECOND = 1000; 50 private static final long ONEMINUTE = 60 * ONESECOND; 51 private static final long ONEHOUR = 60 * ONEMINUTE; 52 private static final long ONEDAY = 24 * ONEHOUR; 53 private static final double ONEYEAR = 365.25 * ONEDAY; // Approximate 54 55 // EModes 56 private static final byte GENERIC = 0; 57 private static final byte TIME = GENERIC + 1; 58 private static final byte DATE = TIME + 1; 59 private static final byte DATE_TIME = DATE + 1; 60 61 private DateFormat fFormat = DateFormat.getInstance(); 62 private String fTestName = new String("getInstance"); 63 private int fLimit = 3; // How many iterations it should take to reach convergence 64 65 public static void main(String[] args) throws Exception { 66 new IntlTestDateFormat().run(args); 67 } 68 69 public void TestLocale() { 70 localeTest(Locale.getDefault(), "Default Locale"); 71 } 72 73 // This test does round-trip testing (format -> parse -> format -> parse -> etc.) of DateFormat. 74 public void localeTest(final Locale locale, final String localeName) { 75 int timeStyle, dateStyle; 76 77 // For patterns including only time information and a timezone, it may take 78 // up to three iterations, since the timezone may shift as the year number 79 // is determined. For other patterns, 2 iterations should suffice. 80 fLimit = 3; 81 82 for(timeStyle = 0; timeStyle < 4; timeStyle++) { 83 fTestName = new String("Time test " + timeStyle + " (" + localeName + ")"); 84 try { 85 fFormat = DateFormat.getTimeInstance(timeStyle, locale); 86 } 87 catch(StringIndexOutOfBoundsException e) { 88 errln("FAIL: localeTest time getTimeInstance exception"); 89 throw e; 90 } 91 TestFormat(); 92 } 93 94 fLimit = 2; 95 96 for(dateStyle = 0; dateStyle < 4; dateStyle++) { 97 fTestName = new String("Date test " + dateStyle + " (" + localeName + ")"); 98 try { 99 fFormat = DateFormat.getDateInstance(dateStyle, locale); 100 } 101 catch(StringIndexOutOfBoundsException e) { 102 errln("FAIL: localeTest date getTimeInstance exception"); 103 throw e; 104 } 105 TestFormat(); 106 } 107 108 for(dateStyle = 0; dateStyle < 4; dateStyle++) { 109 for(timeStyle = 0; timeStyle < 4; timeStyle++) { 110 fTestName = new String("DateTime test " + dateStyle + "/" + timeStyle + " (" + localeName + ")"); 111 try { 112 fFormat = DateFormat.getDateTimeInstance(dateStyle, timeStyle, locale); 113 } 114 catch(StringIndexOutOfBoundsException e) { 115 errln("FAIL: localeTest date/time getDateTimeInstance exception"); 116 throw e; 117 } 118 TestFormat(); 119 } 120 } 121 } 122 123 public void TestFormat() { 124 if (fFormat == null) { 125 errln("FAIL: DateFormat creation failed"); 126 return; 127 } 128 // logln("TestFormat: " + fTestName); 129 Date now = new Date(); 130 tryDate(new Date(0)); 131 tryDate(new Date((long) 1278161801778.0)); 132 tryDate(now); 133 // Shift 6 months into the future, AT THE SAME TIME OF DAY. 134 // This will test the DST handling. 135 tryDate(new Date(now.getTime() + 6*30*ONEDAY)); 136 137 Date limit = new Date(now.getTime() * 10); // Arbitrary limit 138 for (int i=0; i<2; ++i) 139 // tryDate(new Date(floor(randDouble() * limit))); 140 tryDate(new Date((long) (randDouble() * limit.getTime()))); 141 } 142 143 private void describeTest() { 144 if (fFormat == null) { 145 errln("FAIL: no DateFormat"); 146 return; 147 } 148 149 // Assume it's a SimpleDateFormat and get some info 150 SimpleDateFormat s = (SimpleDateFormat) fFormat; 151 logln(fTestName + " Pattern " + s.toPattern()); 152 } 153 154 private void tryDate(Date theDate) { 155 final int DEPTH = 10; 156 Date[] date = new Date[DEPTH]; 157 StringBuffer[] string = new StringBuffer[DEPTH]; 158 159 int dateMatch = 0; 160 int stringMatch = 0; 161 boolean dump = false; 162 int i; 163 for (i=0; i<DEPTH; ++i) string[i] = new StringBuffer(); 164 for (i=0; i<DEPTH; ++i) { 165 if (i == 0) date[i] = theDate; 166 else { 167 try { 168 date[i] = fFormat.parse(string[i-1].toString()); 169 } 170 catch (ParseException e) { 171 describeTest(); 172 errln("********** FAIL: Parse of " + string[i-1] + " failed."); 173 dump = true; 174 break; 175 } 176 } 177 FieldPosition position = new FieldPosition(0); 178 fFormat.format(date[i], string[i], position); 179 if (i > 0) { 180 if (dateMatch == 0 && date[i] == date[i-1]) dateMatch = i; 181 else if (dateMatch > 0 && date[i] != date[i-1]) { 182 describeTest(); 183 errln("********** FAIL: Date mismatch after match."); 184 dump = true; 185 break; 186 } 187 if (stringMatch == 0 && string[i] == string[i-1]) stringMatch = i; 188 else if (stringMatch > 0 && string[i] != string[i-1]) { 189 describeTest(); 190 errln("********** FAIL: String mismatch after match."); 191 dump = true; 192 break; 193 } 194 } 195 if (dateMatch > 0 && stringMatch > 0) break; 196 } 197 if (i == DEPTH) --i; 198 199 if (stringMatch > fLimit || dateMatch > fLimit) { 200 describeTest(); 201 errln("********** FAIL: No string and/or date match within " + fLimit + " iterations."); 202 dump = true; 203 } 204 205 if (dump) { 206 for (int k=0; k<=i; ++k) { 207 logln("" + k + ": " + date[k] + " F> " + string[k] + " P> "); 208 } 209 } 210 } 211 212 // Return a random double from 0.01 to 1, inclusive 213 private double randDouble() { 214 // Assume 8-bit (or larger) rand values. Also assume 215 // that the system rand() function is very poor, which it always is. 216 // double d; 217 // int i; 218 // do { 219 // for (i=0; i < sizeof(double); ++i) 220 // { 221 // char poke = (char*)&d; 222 // poke[i] = (rand() & 0xFF); 223 // } 224 // } while (TPlatformUtilities.isNaN(d) || TPlatformUtilities.isInfinite(d)); 225 226 // if (d < 0.0) d = -d; 227 // if (d > 0.0) 228 // { 229 // double e = floor(log10(d)); 230 // if (e < -2.0) d *= pow(10.0, -e-2); 231 // else if (e > -1.0) d /= pow(10.0, e+1); 232 // } 233 // return d; 234 Random rand = new Random(); 235 return rand.nextDouble(); 236 } 237 238 public void TestAvailableLocales() { 239 final Locale[] locales = DateFormat.getAvailableLocales(); 240 long count = locales.length; 241 logln("" + count + " available locales"); 242 if (locales != null && count != 0) { 243 StringBuffer all = new StringBuffer(); 244 for (int i=0; i<count; ++i) { 245 if (i!=0) all.append(", "); 246 all.append(locales[i].getDisplayName()); 247 } 248 logln(all.toString()); 249 } 250 else errln("********** FAIL: Zero available locales or null array pointer"); 251 } 252 253 /* This test is too slow; we disable it for now 254 public void TestMonster() { 255 final Locale[] locales = DateFormat.getAvailableLocales(); 256 long count = locales.length; 257 if (locales != null && count != 0) { 258 for (int i=0; i<count; ++i) { 259 String name = locales[i].getDisplayName(); 260 logln("Testing " + name + "..."); 261 try { 262 localeTest(locales[i], name); 263 } 264 catch(Exception e) { 265 errln("FAIL: TestMonster localeTest exception" + e); 266 } 267 } 268 } 269 } 270 */ 271} 272 273//eof 274