1 /*
   2  * Copyright (c) 2003, 2014, 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 /* Type-specific source code for unit test
  25  *
  26  * Regenerate the BasicX classes via genBasic.sh whenever this file changes.
  27  * We check in the generated source files so that the test tree can be used
  28  * independently of the rest of the source tree.
  29  */
  30 
  31 // -- This file was mechanically generated: Do not edit! -- //
  32 
  33 import java.io.*;
  34 import java.math.BigDecimal;
  35 import java.math.BigInteger;
  36 import java.text.DateFormatSymbols;
  37 import java.util.*;
  38 
  39 import static java.util.Calendar.*;
  40 
  41 import static java.util.SimpleTimeZone.*;
  42 import java.util.regex.Pattern;
  43 
  44 public class BasicDateTime extends Basic {
  45 
  46     private static void test(String fs, String exp, Object ... args) {
  47         Formatter f = new Formatter(new StringBuilder(), Locale.US);
  48         f.format(fs, args);
  49         ck(fs, exp, f.toString());
  50 
  51         f = new Formatter(new StringBuilder(), Locale.US);
  52         f.format("foo " + fs + " bar", args);
  53         ck(fs, "foo " + exp + " bar", f.toString());
  54     }
  55 
  56     private static void test(Locale l, String fs, String exp, Object ... args)
  57     {
  58         Formatter f = new Formatter(new StringBuilder(), l);
  59         f.format(fs, args);
  60         ck(fs, exp, f.toString());
  61 
  62         f = new Formatter(new StringBuilder(), l);
  63         f.format("foo " + fs + " bar", args);
  64         ck(fs, "foo " + exp + " bar", f.toString());
  65     }
  66 
  67     private static void test(String fs, Object ... args) {
  68         Formatter f = new Formatter(new StringBuilder(), Locale.US);
  69         f.format(fs, args);
  70         ck(fs, "fail", f.toString());
  71     }
  72 
  73     private static void test(String fs) {
  74         Formatter f = new Formatter(new StringBuilder(), Locale.US);
  75         f.format(fs, "fail");
  76         ck(fs, "fail", f.toString());
  77     }
  78 
  79     private static void testSysOut(String fs, String exp, Object ... args) {
  80         FileOutputStream fos = null;
  81         FileInputStream fis = null;
  82         try {
  83             PrintStream saveOut = System.out;
  84             fos = new FileOutputStream("testSysOut");
  85             System.setOut(new PrintStream(fos));
  86             System.out.format(Locale.US, fs, args);
  87             fos.close();
  88 
  89             fis = new FileInputStream("testSysOut");
  90             byte [] ba = new byte[exp.length()];
  91             int len = fis.read(ba);
  92             String got = new String(ba);
  93             if (len != ba.length)
  94                 fail(fs, exp, got);
  95             ck(fs, exp, got);
  96 
  97             System.setOut(saveOut);
  98         } catch (FileNotFoundException ex) {
  99             fail(fs, ex.getClass());
 100         } catch (IOException ex) {
 101             fail(fs, ex.getClass());
 102         } finally {
 103             try {
 104                 if (fos != null)
 105                     fos.close();
 106                 if (fis != null)
 107                     fis.close();
 108             } catch (IOException ex) {
 109                 fail(fs, ex.getClass());
 110             }
 111         }
 112     }
 113 
 114     private static void tryCatch(String fs, Class<?> ex) {
 115         boolean caught = false;
 116         try {
 117             test(fs);
 118         } catch (Throwable x) {
 119             if (ex.isAssignableFrom(x.getClass()))
 120                 caught = true;
 121         }
 122         if (!caught)
 123             fail(fs, ex);
 124         else
 125             pass();
 126     }
 127 
 128     private static void tryCatch(String fs, Class<?> ex, Object ... args) {
 129         boolean caught = false;
 130         try {
 131             test(fs, args);
 132         } catch (Throwable x) {
 133             if (ex.isAssignableFrom(x.getClass()))
 134                 caught = true;
 135         }
 136         if (!caught)
 137             fail(fs, ex);
 138         else
 139             pass();
 140     }
 141 
 142     private static void testDateTime(String fs, String exp, Calendar c) {
 143         testDateTime(fs, exp, c, true);
 144     }
 145 
 146     private static void testDateTime(String fs, String exp, Calendar c, boolean upper) {
 147         //---------------------------------------------------------------------
 148         // Date/Time conversions applicable to Calendar, Date, and long.
 149         //---------------------------------------------------------------------
 150 
 151         // Calendar
 152         test(fs, exp, c);
 153         test((Locale)null, fs, exp, c);
 154         test(Locale.US, fs, exp, c);
 155 
 156         // Date/long do not have timezone information so they will always use
 157         // the default timezone.
 158         String nexp = (fs.equals("%tZ") || fs.equals("%TZ")
 159                        || fs.equals("%tc") || fs.equals("%Tc")
 160                        ? exp.replace("PST", "GMT-08:00")
 161                        : exp);
 162 
 163         // Date (implemented via conversion to Calendar)
 164         Date d = c.getTime();
 165         test(fs, nexp, d);
 166         test((Locale)null, fs, nexp, d);
 167         test(Locale.US, fs, nexp, d);
 168 
 169         // long (implemented via conversion to Calendar)
 170         long l = c.getTimeInMillis();
 171         test(fs, nexp, l);
 172         test((Locale)null, fs, nexp, l);
 173         test(Locale.US, fs, nexp, l);
 174 
 175         if (upper)
 176             // repeat all tests for upper case variant (%T)
 177             testDateTime(Pattern.compile("t").matcher(fs).replaceFirst("T"),
 178                          exp.toUpperCase(), c, false);
 179     }
 180 
 181     private static void testHours() {
 182         for (int i = 0; i < 24; i++) {
 183             // GregorianCalendar(int year, int month, int dayOfMonth,
 184             //    int hourOfDay, int minute, int second);
 185             Calendar c = new GregorianCalendar(1995, MAY, 23, i, 48, 34);
 186 
 187             //-----------------------------------------------------------------
 188             // DateTime.HOUR_OF_DAY - 'k' (0 - 23) -- like H
 189             //-----------------------------------------------------------------
 190             String exp = Integer.toString(i);
 191             testDateTime("%tk", exp, c);
 192 
 193             //-----------------------------------------------------------------
 194             // DateTime.HOUR - 'l' (1 - 12) -- like I
 195             //-----------------------------------------------------------------
 196             int v = i % 12;
 197             v = (v == 0 ? 12 : v);
 198             String exp2 = Integer.toString(v);
 199             testDateTime("%tl", exp2, c);
 200 
 201             //-----------------------------------------------------------------
 202             // DateTime.HOUR_OF_DAY_0 - 'H' (00 - 23) [zero padded]
 203             //-----------------------------------------------------------------
 204             if (exp.length() < 2) exp = "0" + exp;
 205             testDateTime("%tH", exp, c);
 206 
 207             //-----------------------------------------------------------------
 208             // DateTime.HOUR_0 - 'I' (01 - 12)
 209             //-----------------------------------------------------------------
 210             if (exp2.length() < 2) exp2 = "0" + exp2;
 211             testDateTime("%tI", exp2, c);
 212 
 213             //-----------------------------------------------------------------
 214             // DateTime.AM_PM - (am or pm)
 215             //-----------------------------------------------------------------
 216             testDateTime("%tp", (i <12 ? "am" : "pm"), c);
 217         }
 218     }
 219 
 220     public static void test() {
 221         TimeZone.setDefault(TimeZone.getTimeZone("GMT-0800"));
 222 
 223         // Any characters not explicitly defined as conversions, date/time
 224         // conversion suffixes, or flags are illegal and are reserved for
 225         // future extensions.  Use of such a character in a format string will
 226         // cause an UnknownFormatConversionException or
 227         // UnknownFormatFlagsException to be thrown.
 228         tryCatch("%q", UnknownFormatConversionException.class);
 229         tryCatch("%t&", UnknownFormatConversionException.class);
 230         tryCatch("%&d", UnknownFormatConversionException.class);
 231         tryCatch("%^b", UnknownFormatConversionException.class);
 232 
 233         //---------------------------------------------------------------------
 234         // Formatter.java class javadoc examples
 235         //---------------------------------------------------------------------
 236         test(Locale.FRANCE, "e = %+10.4f", "e =    +2,7183", Math.E);
 237         test("%4$2s %3$2s %2$2s %1$2s", " d  c  b  a", "a", "b", "c", "d");
 238         test("Amount gained or lost since last statement: $ %,(.2f",
 239              "Amount gained or lost since last statement: $ (6,217.58)",
 240              (new BigDecimal("-6217.58")));
 241         Calendar c = new GregorianCalendar(1969, JULY, 20, 16, 17, 0);
 242         testSysOut("Local time: %tT", "Local time: 16:17:00", c);
 243 
 244         test("Unable to open file '%1$s': %2$s",
 245              "Unable to open file 'food': No such file or directory",
 246              "food", "No such file or directory");
 247         Calendar duke = new GregorianCalendar(1995, MAY, 23, 19, 48, 34);
 248         duke.set(Calendar.MILLISECOND, 584);
 249         test("Duke's Birthday: %1$tB %1$te, %1$tY",
 250              "Duke's Birthday: May 23, 1995",
 251              duke);
 252         test("Duke's Birthday: %1$tB %1$te, %1$tY",
 253              "Duke's Birthday: May 23, 1995",
 254              duke.getTime());
 255         test("Duke's Birthday: %1$tB %1$te, %1$tY",
 256              "Duke's Birthday: May 23, 1995",
 257              duke.getTimeInMillis());
 258 
 259         test("%4$s %3$s %2$s %1$s %4$s %3$s %2$s %1$s",
 260              "d c b a d c b a", "a", "b", "c", "d");
 261         test("%s %s %<s %<s", "a b b b", "a", "b", "c", "d");
 262         test("%s %s %s %s", "a b c d", "a", "b", "c", "d");
 263         test("%2$s %s %<s %s", "b a a b", "a", "b", "c", "d");
 264 
 265         //---------------------------------------------------------------------
 266         // %b
 267         //
 268         // General conversion applicable to any argument.
 269         //---------------------------------------------------------------------
 270         test("%b", "true", true);
 271         test("%b", "false", false);
 272         test("%B", "TRUE", true);
 273         test("%B", "FALSE", false);
 274         test("%b", "true", Boolean.TRUE);
 275         test("%b", "false", Boolean.FALSE);
 276         test("%B", "TRUE", Boolean.TRUE);
 277         test("%B", "FALSE", Boolean.FALSE);
 278         test("%14b", "          true", true);
 279         test("%-14b", "true          ", true);
 280         test("%5.1b", "    f", false);
 281         test("%-5.1b", "f    ", false);
 282 
 283         test("%b", "true", "foo");
 284         test("%b", "false", (Object)null);
 285 
 286         // Boolean.java hardcodes the Strings for "true" and "false", so no
 287         // localization is possible.
 288         test(Locale.FRANCE, "%b", "true", true);
 289         test(Locale.FRANCE, "%b", "false", false);
 290 
 291         // If you pass in a single array to a varargs method, the compiler
 292         // uses it as the array of arguments rather than treating it as a
 293         // single array-type argument.
 294         test("%b", "false", (Object[])new String[2]);
 295         test("%b", "true", new String[2], new String[2]);
 296 
 297         int [] ia = { 1, 2, 3 };
 298         test("%b", "true", ia);
 299 
 300         //---------------------------------------------------------------------
 301         // %b - errors
 302         //---------------------------------------------------------------------
 303         tryCatch("%#b", FormatFlagsConversionMismatchException.class);
 304         tryCatch("%-b", MissingFormatWidthException.class);
 305         // correct or side-effect of implementation?
 306         tryCatch("%.b", UnknownFormatConversionException.class);
 307         tryCatch("%,b", FormatFlagsConversionMismatchException.class);
 308 
 309         //---------------------------------------------------------------------
 310         // %c
 311         //
 312         // General conversion applicable to any argument.
 313         //---------------------------------------------------------------------
 314         test("%c", "i", 'i');
 315         test("%C", "I", 'i');
 316         test("%4c",  "   i", 'i');
 317         test("%-4c", "i   ", 'i');
 318         test("%4C",  "   I", 'i');
 319         test("%-4C", "I   ", 'i');
 320         test("%c", "i", new Character('i'));
 321         test("%c", "H", (byte) 72);
 322         test("%c", "i", (short) 105);
 323         test("%c", "!", (int) 33);
 324         test("%c", "\u007F", Byte.MAX_VALUE);
 325         test("%c", new String(Character.toChars(Short.MAX_VALUE)),
 326              Short.MAX_VALUE);
 327         test("%c", "null", (Object) null);
 328 
 329         //---------------------------------------------------------------------
 330         // %c - errors
 331         //---------------------------------------------------------------------
 332         tryCatch("%c", IllegalFormatConversionException.class,
 333                  Boolean.TRUE);
 334         tryCatch("%c", IllegalFormatConversionException.class,
 335                  (float) 0.1);
 336         tryCatch("%c", IllegalFormatConversionException.class,
 337                  new Object());
 338         tryCatch("%c", IllegalFormatCodePointException.class,
 339                  Byte.MIN_VALUE);
 340         tryCatch("%c", IllegalFormatCodePointException.class,
 341                  Short.MIN_VALUE);
 342         tryCatch("%c", IllegalFormatCodePointException.class,
 343                  Integer.MIN_VALUE);
 344         tryCatch("%c", IllegalFormatCodePointException.class,
 345                  Integer.MAX_VALUE);
 346 
 347         tryCatch("%#c", FormatFlagsConversionMismatchException.class);
 348         tryCatch("%,c", FormatFlagsConversionMismatchException.class);
 349         tryCatch("%(c", FormatFlagsConversionMismatchException.class);
 350         tryCatch("%$c", UnknownFormatConversionException.class);
 351         tryCatch("%.2c", IllegalFormatPrecisionException.class);
 352 
 353         //---------------------------------------------------------------------
 354         // %s
 355         //
 356         // General conversion applicable to any argument.
 357         //---------------------------------------------------------------------
 358         test("%s", "Hello, Duke", "Hello, Duke");
 359         test("%S", "HELLO, DUKE", "Hello, Duke");
 360         test("%20S", "         HELLO, DUKE", "Hello, Duke");
 361         test("%20s", "         Hello, Duke", "Hello, Duke");
 362         test("%-20s", "Hello, Duke         ", "Hello, Duke");
 363         test("%-20.5s", "Hello               ", "Hello, Duke");
 364         test("%s", "null", (Object)null);
 365 
 366         StringBuffer sb = new StringBuffer("foo bar");
 367         test("%s", sb.toString(), sb);
 368         test("%S", sb.toString().toUpperCase(), sb);
 369 
 370         //---------------------------------------------------------------------
 371         // %s - errors
 372         //---------------------------------------------------------------------
 373         tryCatch("%-s", MissingFormatWidthException.class);
 374         tryCatch("%--s", DuplicateFormatFlagsException.class);
 375         tryCatch("%#s", FormatFlagsConversionMismatchException.class, 0);
 376         tryCatch("%#s", FormatFlagsConversionMismatchException.class, 0.5f);
 377         tryCatch("%#s", FormatFlagsConversionMismatchException.class, "hello");
 378         tryCatch("%#s", FormatFlagsConversionMismatchException.class, null);
 379 
 380         //---------------------------------------------------------------------
 381         // %h
 382         //
 383         // General conversion applicable to any argument.
 384         //---------------------------------------------------------------------
 385         test("%h", Integer.toHexString("Hello, Duke".hashCode()),
 386              "Hello, Duke");
 387         test("%10h", "  ddf63471", "Hello, Duke");
 388         test("%-10h", "ddf63471  ", "Hello, Duke");
 389         test("%-10H", "DDF63471  ", "Hello, Duke");
 390         test("%10h", "  402e0000", 15.0);
 391         test("%10H", "  402E0000", 15.0);
 392 
 393         //---------------------------------------------------------------------
 394         // %h - errors
 395         //---------------------------------------------------------------------
 396         tryCatch("%#h", FormatFlagsConversionMismatchException.class);
 397 
 398         //---------------------------------------------------------------------
 399         // flag/conversion errors
 400         //---------------------------------------------------------------------
 401         tryCatch("%F", UnknownFormatConversionException.class);
 402 
 403         tryCatch("%#g", FormatFlagsConversionMismatchException.class);
 404 
 405         //---------------------------------------------------------------------
 406         // %t
 407         //
 408         // Date/Time conversions applicable to Calendar, Date, and long.
 409         //---------------------------------------------------------------------
 410         test("%tA", "null", (Object)null);
 411         test("%TA", "NULL", (Object)null);
 412 
 413         //---------------------------------------------------------------------
 414         // %t - errors
 415         //---------------------------------------------------------------------
 416         tryCatch("%t", UnknownFormatConversionException.class);
 417         tryCatch("%T", UnknownFormatConversionException.class);
 418         tryCatch("%tP", UnknownFormatConversionException.class);
 419         tryCatch("%TP", UnknownFormatConversionException.class);
 420         tryCatch("%.5tB", IllegalFormatPrecisionException.class);
 421         tryCatch("%#tB", FormatFlagsConversionMismatchException.class);
 422         tryCatch("%-tB", MissingFormatWidthException.class);
 423 
 424         //---------------------------------------------------------------------
 425         // %t - create test Calendar
 426         //---------------------------------------------------------------------
 427 
 428         // Get the supported ids for GMT-08:00 (Pacific Standard Time)
 429         String[] ids = TimeZone.getAvailableIDs(-8 * 60 * 60 * 1000);
 430         // Create a Pacific Standard Time time zone
 431         SimpleTimeZone tz = new SimpleTimeZone(-8 * 60 * 60 * 1000, ids[0]);
 432         // public GregorianCalendar(TimeZone zone, Locale aLocale);
 433         Calendar c0 = new GregorianCalendar(tz, Locale.US);
 434         // public final void set(int year, int month, int date,
 435         //     int hourOfDay, int minute, int second);
 436         c0.set(1995, MAY, 23, 19, 48, 34);
 437         c0.set(Calendar.MILLISECOND, 584);
 438 
 439         //---------------------------------------------------------------------
 440         // %t - Minutes, {nano,milli}*seconds
 441         //
 442         // testDateTime() verifies the expected output for all applicable types
 443         // (Calendar, Date, and long).  It also verifies output for "%t" and
 444         // "%T". Thus it is sufficient to invoke that method once per
 445         // conversion/expected output.
 446         //---------------------------------------------------------------------
 447         testDateTime("%tM", "48", c0);
 448         testDateTime("%tN", "584000000", c0);
 449         testDateTime("%tL", "584", c0);
 450 //      testDateTime("%tQ", "801283714584", c0);
 451 
 452         testDateTime("%ts", String.valueOf(c0.getTimeInMillis() / 1000), c0);
 453         testDateTime("%tS", "34", c0);
 454         testDateTime("%tT", "19:48:34", c0);
 455 
 456         //---------------------------------------------------------------------
 457         // %t - Hours, morning/afternoon markers
 458         //
 459         // testHours() iterates through all twenty-four hours to verify
 460         // numeric return value and morning/afternoon markers.
 461         //---------------------------------------------------------------------
 462         testHours();
 463 
 464         //---------------------------------------------------------------------
 465         // %t - Portions of date [ day, month, dates, weeks ]
 466         //---------------------------------------------------------------------
 467         testDateTime("%ta", "Tue", c0);
 468         testDateTime("%tA", "Tuesday", c0);
 469         testDateTime("%tb", "May", c0);
 470         testDateTime("%tB", "May", c0);
 471         testDateTime("%tC", "19", c0);
 472         testDateTime("%td", "23", c0);
 473         testDateTime("%te", "23", c0);
 474         testDateTime("%th", "May", c0);
 475         testDateTime("%tj", "143", c0);
 476         testDateTime("%tm", "05", c0);
 477         testDateTime("%ty", "95", c0);
 478         testDateTime("%tY", "1995", c0);
 479 
 480         //---------------------------------------------------------------------
 481         // %t - TimeZone
 482         //---------------------------------------------------------------------
 483         testDateTime("%tz", "-0800", c0);
 484         testDateTime("%tZ", "PST", c0);
 485 
 486         //---------------------------------------------------------------------
 487         // %tz should always adjust for DST
 488         //---------------------------------------------------------------------
 489         TimeZone dtz = TimeZone.getDefault();
 490 
 491         // Artificial TimeZone based on PST with 3:15 DST always in effect
 492         TimeZone atz = new SimpleTimeZone(-8 * 60 * 60 * 1000, "AlwaysDST",
 493             JANUARY, 1, 0, 0, STANDARD_TIME,
 494             // 24hrs - 1m = 60 * 60 * 1000 * 24 - 1
 495             DECEMBER, 31, 0, 60 * 60 * 1000 * 24 - 1, STANDARD_TIME,
 496             (int)(60 * 60 * 1000 * 3.25));
 497         TimeZone.setDefault(atz);
 498         testDateTime("%tz", "-0445", Calendar.getInstance(atz));
 499 
 500         // Restore the TimeZone and verify
 501         TimeZone.setDefault(dtz);
 502         if (atz.hasSameRules(TimeZone.getDefault()))
 503             throw new RuntimeException("Default TimeZone not restored");
 504 
 505         //---------------------------------------------------------------------
 506         // %t - Composites
 507         //---------------------------------------------------------------------
 508         testDateTime("%tr", "07:48:34 PM", c0);
 509         testDateTime("%tR", "19:48", c0);
 510         testDateTime("%tc", "Tue May 23 19:48:34 PST 1995", c0);
 511         testDateTime("%tD", "05/23/95", c0);
 512         testDateTime("%tF", "1995-05-23", c0);
 513         testDateTime("%-12tF", "1995-05-23  ", c0);
 514         testDateTime("%12tF", "  1995-05-23", c0);
 515 
 516         //---------------------------------------------------------------------
 517         // %n
 518         //---------------------------------------------------------------------
 519         test("%n", System.getProperty("line.separator"), (Object)null);
 520         test("%n", System.getProperty("line.separator"), "");
 521 
 522         tryCatch("%,n", IllegalFormatFlagsException.class);
 523         tryCatch("%.n", UnknownFormatConversionException.class);
 524         tryCatch("%5.n", UnknownFormatConversionException.class);
 525         tryCatch("%5n", IllegalFormatWidthException.class);
 526         tryCatch("%.7n", IllegalFormatPrecisionException.class);
 527         tryCatch("%<n", IllegalFormatFlagsException.class);
 528 
 529         //---------------------------------------------------------------------
 530         // %%
 531         //---------------------------------------------------------------------
 532         test("%%", "%", (Object)null);
 533         test("%%", "%", "");
 534         tryCatch("%%%", UnknownFormatConversionException.class);
 535         // perhaps an IllegalFormatArgumentIndexException should be defined?
 536         tryCatch("%<%", IllegalFormatFlagsException.class);
 537     }
 538 }