test/java/time/tck/java/time/format/TCKDateTimeFormatter.java

Print this page




  44  *  * Neither the name of JSR-310 nor the names of its contributors
  45  *    may be used to endorse or promote products derived from this software
  46  *    without specific prior written permission.
  47  *
  48  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
  49  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
  50  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
  51  * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
  52  * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
  53  * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
  54  * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
  55  * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
  56  * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
  57  * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
  58  * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  59  */
  60 package tck.java.time.format;
  61 
  62 import static java.time.temporal.ChronoField.DAY_OF_MONTH;
  63 import static java.time.temporal.ChronoField.HOUR_OF_DAY;

  64 import static java.time.temporal.ChronoField.YEAR;
  65 import static org.testng.Assert.assertEquals;
  66 import static org.testng.Assert.assertNull;
  67 import static org.testng.Assert.assertTrue;

  68 
  69 import java.io.IOException;
  70 import java.text.Format;
  71 import java.text.ParseException;
  72 import java.text.ParsePosition;
  73 import java.util.Locale;
  74 
  75 import java.time.DateTimeException;
  76 import java.time.Instant;
  77 import java.time.LocalDate;
  78 import java.time.LocalDateTime;
  79 import java.time.LocalTime;
  80 import java.time.ZoneId;
  81 import java.time.ZoneOffset;
  82 import java.time.ZonedDateTime;
  83 import java.time.calendar.ThaiBuddhistChrono;
  84 import java.time.format.DateTimeFormatSymbols;
  85 import java.time.format.DateTimeFormatter;
  86 import java.time.format.DateTimeFormatterBuilder;
  87 import java.time.format.DateTimeFormatters;
  88 import java.time.format.DateTimeParseException;
  89 import java.time.format.DateTimePrintException;
  90 import java.time.format.SignStyle;
  91 import java.time.format.DateTimeBuilder;
  92 import java.time.temporal.Chrono;
  93 import java.time.temporal.ISOChrono;
  94 import java.time.temporal.OffsetDate;
  95 import java.time.temporal.OffsetDateTime;
  96 import java.time.temporal.OffsetTime;
  97 import java.time.temporal.Temporal;
  98 import java.time.temporal.TemporalAccessor;
  99 import java.time.temporal.TemporalQuery;
 100 
 101 import org.testng.annotations.BeforeMethod;
 102 import org.testng.annotations.DataProvider;
 103 import org.testng.annotations.Test;
 104 import test.java.time.format.MockIOExceptionAppendable;
 105 
 106 /**
 107  * Test DateTimeFormatter.
 108  */
 109 @Test(groups={"tck"})
 110 public class TCKDateTimeFormatter {
 111 
 112     private static final ZoneOffset OFFSET_PONE = ZoneOffset.ofHours(1);
 113     private static final ZoneOffset OFFSET_PTHREE = ZoneOffset.ofHours(3);
 114     private static final ZoneId ZONE_PARIS = ZoneId.of("Europe/Paris");
 115 
 116     private static final DateTimeFormatter BASIC_FORMATTER = DateTimeFormatters.pattern("'ONE'd");
 117     private static final DateTimeFormatter DATE_FORMATTER = DateTimeFormatters.pattern("'ONE'yyyy MM dd");
 118 
 119     private DateTimeFormatter fmt;
 120 
 121     @BeforeMethod
 122     public void setUp() {
 123         fmt = new DateTimeFormatterBuilder().appendLiteral("ONE")
 124                                             .appendValue(DAY_OF_MONTH, 1, 2, SignStyle.NOT_NEGATIVE)
 125                                             .toFormatter();
 126     }
 127 
 128     //-----------------------------------------------------------------------
 129     @Test
 130     public void test_withLocale() {
 131         DateTimeFormatter base = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 132         DateTimeFormatter test = base.withLocale(Locale.GERMAN);
 133         assertEquals(test.getLocale(), Locale.GERMAN);
 134     }
 135 
 136     @Test(expectedExceptions=NullPointerException.class)
 137     public void test_withLocale_null() {
 138         DateTimeFormatter base = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 139         base.withLocale((Locale) null);
 140     }
 141 
 142     //-----------------------------------------------------------------------
 143     @Test
 144     public void test_withChrono() {
 145         DateTimeFormatter test = fmt;
 146         assertEquals(test.getChrono(), null);
 147         test = test.withChrono(ISOChrono.INSTANCE);
 148         assertEquals(test.getChrono(), ISOChrono.INSTANCE);
 149         test = test.withChrono(null);
 150         assertEquals(test.getChrono(), null);
 151     }
 152 
 153     //-----------------------------------------------------------------------
 154     @Test
 155     public void test_withZone() {
 156         DateTimeFormatter test = fmt;
 157         assertEquals(test.getZone(), null);
 158         test = test.withZone(ZoneId.of("Europe/Paris"));
 159         assertEquals(test.getZone(), ZoneId.of("Europe/Paris"));
 160         test = test.withZone(ZoneOffset.UTC);
 161         assertEquals(test.getZone(), ZoneOffset.UTC);
 162         test = test.withZone(null);
 163         assertEquals(test.getZone(), null);
 164     }
 165 
 166     //-----------------------------------------------------------------------
 167     // print
 168     //-----------------------------------------------------------------------
 169     @DataProvider(name="print")
 170     Object[][] data_print() {
 171         LocalDate ld = LocalDate.of(2008, 6, 30);
 172         LocalTime lt = LocalTime.of(11, 30);
 173         LocalDateTime ldt = LocalDateTime.of(2008, 6, 30, 11, 30);
 174         OffsetDate od = OffsetDate.of(LocalDate.of(2008, 6, 30), OFFSET_PONE);
 175         OffsetTime ot = OffsetTime.of(LocalTime.of(11, 30), OFFSET_PONE);
 176         OffsetDateTime odt = OffsetDateTime.of(LocalDateTime.of(2008, 6, 30, 11, 30), OFFSET_PONE);
 177         ZonedDateTime zdt = ZonedDateTime.of(LocalDateTime.of(2008, 6, 30, 11, 30), ZONE_PARIS);
 178         Instant instant = Instant.ofEpochSecond(3600);
 179         return new Object[][] {
 180                 {null, null, ld, "2008::"},
 181                 {null, null, lt, ":11:"},
 182                 {null, null, ldt, "2008:11:"},
 183                 {null, null, od, "2008::+01:00"},
 184                 {null, null, ot, ":11:+01:00"},
 185                 {null, null, odt, "2008:11:+01:00"},
 186                 {null, null, zdt, "2008:11:+02:00Europe/Paris"},
 187                 {null, null, instant, "::"},
 188 
 189                 {null, ZONE_PARIS, ld, "2008::"},
 190                 {null, ZONE_PARIS, lt, ":11:"},
 191                 {null, ZONE_PARIS, ldt, "2008:11:"},
 192                 {null, ZONE_PARIS, od, "2008::+01:00"},
 193                 {null, ZONE_PARIS, ot, ":11:+01:00"},
 194                 {null, ZONE_PARIS, odt, "2008:12:+02:00Europe/Paris"},
 195                 {null, ZONE_PARIS, zdt, "2008:11:+02:00Europe/Paris"},
 196                 {null, ZONE_PARIS, instant, "1970:02:+01:00Europe/Paris"},
 197 
 198                 {null, OFFSET_PTHREE, ld, "2008::"},
 199                 {null, OFFSET_PTHREE, lt, ":11:"},
 200                 {null, OFFSET_PTHREE, ldt, "2008:11:"},
 201                 {null, OFFSET_PTHREE, od, "2008::+01:00"},
 202                 {null, OFFSET_PTHREE, ot, ":11:+01:00"},
 203                 {null, OFFSET_PTHREE, odt, "2008:13:+03:00"},
 204                 {null, OFFSET_PTHREE, zdt, "2008:12:+03:00"},
 205                 {null, OFFSET_PTHREE, instant, "1970:04:+03:00"},
 206 
 207                 {ThaiBuddhistChrono.INSTANCE, null, ld, "2551::"},
 208                 {ThaiBuddhistChrono.INSTANCE, null, lt, ":11:"},
 209                 {ThaiBuddhistChrono.INSTANCE, null, ldt, "2551:11:"},
 210                 {ThaiBuddhistChrono.INSTANCE, null, od, "2551::+01:00"},
 211                 {ThaiBuddhistChrono.INSTANCE, null, ot, ":11:+01:00"},
 212                 {ThaiBuddhistChrono.INSTANCE, null, odt, "2551:11:+01:00"},
 213                 {ThaiBuddhistChrono.INSTANCE, null, zdt, "2551:11:+02:00Europe/Paris"},
 214                 {ThaiBuddhistChrono.INSTANCE, null, instant, "::"},
 215 
 216                 {ThaiBuddhistChrono.INSTANCE, ZONE_PARIS, ld, "2551::"},
 217                 {ThaiBuddhistChrono.INSTANCE, ZONE_PARIS, lt, ":11:"},
 218                 {ThaiBuddhistChrono.INSTANCE, ZONE_PARIS, ldt, "2551:11:"},
 219                 {ThaiBuddhistChrono.INSTANCE, ZONE_PARIS, od, "2551::+01:00"},
 220                 {ThaiBuddhistChrono.INSTANCE, ZONE_PARIS, ot, ":11:+01:00"},
 221                 {ThaiBuddhistChrono.INSTANCE, ZONE_PARIS, odt, "2551:12:+02:00Europe/Paris"},
 222                 {ThaiBuddhistChrono.INSTANCE, ZONE_PARIS, zdt, "2551:11:+02:00Europe/Paris"},
 223                 {ThaiBuddhistChrono.INSTANCE, ZONE_PARIS, instant, "1970:02:+01:00Europe/Paris"},
 224         };
 225     }
 226 
 227     @Test(dataProvider="print")
 228     public void test_print_Temporal(Chrono<?> overrideChrono, ZoneId overrideZone, Temporal temporal, String expected) {
 229         DateTimeFormatter test = new DateTimeFormatterBuilder()
 230                 .optionalStart().appendValue(YEAR, 4).optionalEnd()
 231                 .appendLiteral(':').optionalStart().appendValue(HOUR_OF_DAY, 2).optionalEnd()
 232                 .appendLiteral(':').optionalStart().appendOffsetId().optionalStart().appendZoneRegionId().optionalEnd().optionalEnd()
 233                 .toFormatter(Locale.ENGLISH)
 234                 .withChrono(overrideChrono).withZone(overrideZone);
 235         String result = test.print(temporal);
 236         assertEquals(result, expected);
 237     }
 238 
 239     @Test
 240     public void test_print_Temporal_simple() throws Exception {
 241         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 242         String result = test.print(LocalDate.of(2008, 6, 30));
 243         assertEquals(result, "ONE30");
 244     }
 245 
 246     @Test(expectedExceptions=DateTimeException.class)
 247     public void test_print_Temporal_noSuchField() throws Exception {
 248         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 249         test.print(LocalTime.of(11, 30));
 250     }
 251 
 252     @Test(expectedExceptions=NullPointerException.class)
 253     public void test_print_Temporal_null() throws Exception {
 254         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 255         test.print((TemporalAccessor) null);
 256     }
 257 
 258     //-----------------------------------------------------------------------
 259     @Test
 260     public void test_print_TemporalAppendable() throws Exception {
 261         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 262         StringBuilder buf = new StringBuilder();
 263         test.printTo(LocalDate.of(2008, 6, 30), buf);
 264         assertEquals(buf.toString(), "ONE30");
 265     }
 266 
 267     @Test(expectedExceptions=DateTimeException.class)
 268     public void test_print_TemporalAppendable_noSuchField() throws Exception {
 269         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 270         StringBuilder buf = new StringBuilder();
 271         test.printTo(LocalTime.of(11, 30), buf);
 272     }
 273 
 274     @Test(expectedExceptions=NullPointerException.class)
 275     public void test_print_TemporalAppendable_nullTemporal() throws Exception {
 276         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 277         StringBuilder buf = new StringBuilder();
 278         test.printTo((TemporalAccessor) null, buf);
 279     }
 280 
 281     @Test(expectedExceptions=NullPointerException.class)
 282     public void test_print_TemporalAppendable_nullAppendable() throws Exception {
 283         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 284         test.printTo(LocalDate.of(2008, 6, 30), (Appendable) null);
 285     }
 286 
 287     @Test(expectedExceptions=IOException.class)  // IOException
 288     public void test_print_TemporalAppendable_ioError() throws Exception {


























 289         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);







































 290         try {
 291             test.printTo(LocalDate.of(2008, 6, 30), new MockIOExceptionAppendable());
 292         } catch (DateTimePrintException ex) {
 293             assertEquals(ex.getCause() instanceof IOException, true);
 294             ex.rethrowIOException();














 295         }





 296     }
 297 
 298     //-----------------------------------------------------------------------
 299     // parse(Query)
 300     //-----------------------------------------------------------------------
 301     @Test
 302     public void test_parse_Query_String() throws Exception {
 303         LocalDate result = DATE_FORMATTER.parse("ONE2012 07 27", LocalDate::from);
 304         assertEquals(result, LocalDate.of(2012, 7, 27));
 305     }
 306 
 307     @Test
 308     public void test_parse_Query_CharSequence() throws Exception {
 309         LocalDate result = DATE_FORMATTER.parse(new StringBuilder("ONE2012 07 27"), LocalDate::from);
 310         assertEquals(result, LocalDate.of(2012, 7, 27));
 311     }
 312 
 313     @Test(expectedExceptions=DateTimeParseException.class)
 314     public void test_parse_Query_String_parseError() throws Exception {
 315         try {


 346             assertEquals(ex.getParsedString(), "ONE2012 07 27SomethingElse");
 347             assertEquals(ex.getErrorIndex(), 13);
 348             throw ex;
 349         }
 350     }
 351 
 352     @Test(expectedExceptions=NullPointerException.class)
 353     public void test_parse_Query_String_nullText() throws Exception {
 354         DATE_FORMATTER.parse((String) null, LocalDate::from);
 355     }
 356 
 357     @Test(expectedExceptions=NullPointerException.class)
 358     public void test_parse_Query_String_nullRule() throws Exception {
 359         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 360         test.parse("30", (TemporalQuery<?>) null);
 361     }
 362 
 363     //-----------------------------------------------------------------------
 364     @Test
 365     public void test_parseBest_firstOption() throws Exception {
 366         DateTimeFormatter test = DateTimeFormatters.pattern("yyyy-MM-dd[ZZZ]");
 367         TemporalAccessor result = test.parseBest("2011-06-30+03:00", OffsetDate::from, LocalDate::from);
 368         assertEquals(result, OffsetDate.of(LocalDate.of(2011, 6, 30), ZoneOffset.ofHours(3)));

 369     }
 370 
 371     @Test
 372     public void test_parseBest_secondOption() throws Exception {
 373         DateTimeFormatter test = DateTimeFormatters.pattern("yyyy-MM-dd[ZZZ]");
 374         TemporalAccessor result = test.parseBest("2011-06-30", OffsetDate::from, LocalDate::from);
 375         assertEquals(result, LocalDate.of(2011, 6, 30));
 376     }
 377 
 378     @Test(expectedExceptions=DateTimeParseException.class)
 379     public void test_parseBest_String_parseError() throws Exception {
 380         DateTimeFormatter test = DateTimeFormatters.pattern("yyyy-MM-dd[ZZZ]");
 381         try {
 382             test.parseBest("2011-06-XX", OffsetDate::from, LocalDate::from);
 383         } catch (DateTimeParseException ex) {
 384             assertEquals(ex.getMessage().contains("could not be parsed"), true);
 385             assertEquals(ex.getMessage().contains("XX"), true);
 386             assertEquals(ex.getParsedString(), "2011-06-XX");
 387             assertEquals(ex.getErrorIndex(), 8);
 388             throw ex;
 389         }
 390     }
 391 
 392     @Test(expectedExceptions=DateTimeParseException.class)
 393     public void test_parseBest_String_parseErrorLongText() throws Exception {
 394         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 395         try {
 396             test.parseBest("ONEXXX67890123456789012345678901234567890123456789012345678901234567890123456789", LocalDate::from, OffsetDate::from);
 397         } catch (DateTimeParseException ex) {
 398             assertEquals(ex.getMessage().contains("could not be parsed"), true);
 399             assertEquals(ex.getMessage().contains("ONEXXX6789012345678901234567890123456789012345678901234567890123..."), true);
 400             assertEquals(ex.getParsedString(), "ONEXXX67890123456789012345678901234567890123456789012345678901234567890123456789");
 401             assertEquals(ex.getErrorIndex(), 3);
 402             throw ex;
 403         }
 404     }
 405 
 406     @Test(expectedExceptions=DateTimeParseException.class)
 407     public void test_parseBest_String_parseIncomplete() throws Exception {
 408         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 409         try {
 410             test.parseBest("ONE30SomethingElse", LocalDate::from, OffsetDate::from);
 411         } catch (DateTimeParseException ex) {
 412             assertEquals(ex.getMessage().contains("could not be parsed"), true);
 413             assertEquals(ex.getMessage().contains("ONE30SomethingElse"), true);
 414             assertEquals(ex.getParsedString(), "ONE30SomethingElse");
 415             assertEquals(ex.getErrorIndex(), 5);
 416             throw ex;
 417         }
 418     }
 419 
 420     @Test(expectedExceptions=NullPointerException.class)
 421     public void test_parseBest_String_nullText() throws Exception {
 422         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 423         test.parseBest((String) null, LocalDate::from, OffsetDate::from);
 424     }
 425 
 426     @Test(expectedExceptions=NullPointerException.class)
 427     public void test_parseBest_String_nullRules() throws Exception {
 428         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 429         test.parseBest("30", (TemporalQuery<?>[]) null);
 430     }
 431 
 432     @Test(expectedExceptions=IllegalArgumentException.class)
 433     public void test_parseBest_String_zeroRules() throws Exception {
 434         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 435         test.parseBest("30", new TemporalQuery<?>[0]);
 436     }
 437 
 438     @Test(expectedExceptions=IllegalArgumentException.class)
 439     public void test_parseBest_String_oneRule() throws Exception {
 440         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 441         test.parseBest("30", LocalDate::from);
 442     }
 443 
 444     //-----------------------------------------------------------------------
 445     @Test
 446     public void test_parseToBuilder_String() throws Exception {
 447         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 448         DateTimeBuilder result = test.parseToBuilder("ONE30");
 449         assertEquals(result.getFieldValueMap().size(), 1);
 450         assertEquals(result.getFieldValue(DAY_OF_MONTH), 30L);
 451         assertEquals(result.getCalendricalList().size(), 0);

 452     }
 453 
 454     @Test
 455     public void test_parseToBuilder_CharSequence() throws Exception {
 456         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 457         DateTimeBuilder result = test.parseToBuilder(new StringBuilder("ONE30"));
 458         assertEquals(result.getFieldValueMap().size(), 1);
 459         assertEquals(result.getFieldValue(DAY_OF_MONTH), 30L);
 460         assertEquals(result.getCalendricalList().size(), 0);
 461     }
 462 
 463     @Test(expectedExceptions=DateTimeParseException.class)
 464     public void test_parseToBuilder_String_parseError() throws Exception {
 465         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 466         try {
 467             test.parseToBuilder("ONEXXX");
 468         } catch (DateTimeParseException ex) {
 469             assertEquals(ex.getMessage().contains("ONEXXX"), true);
 470             assertEquals(ex.getParsedString(), "ONEXXX");
 471             assertEquals(ex.getErrorIndex(), 3);
 472             throw ex;
 473         }
 474     }
 475 
 476     @Test(expectedExceptions=DateTimeParseException.class)
 477     public void test_parseToBuilder_String_parseErrorLongText() throws Exception {
 478         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 479         try {
 480             test.parseToBuilder("ONEXXX67890123456789012345678901234567890123456789012345678901234567890123456789");
 481         } catch (DateTimeParseException ex) {
 482             assertEquals(ex.getMessage().contains("ONEXXX6789012345678901234567890123456789012345678901234567890123..."), true);
 483             assertEquals(ex.getParsedString(), "ONEXXX67890123456789012345678901234567890123456789012345678901234567890123456789");
 484             assertEquals(ex.getErrorIndex(), 3);
 485             throw ex;
 486         }
 487     }
 488 
 489     @Test(expectedExceptions=DateTimeParseException.class)
 490     public void test_parseToBuilder_String_parseIncomplete() throws Exception {
 491         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 492         try {
 493             test.parseToBuilder("ONE30SomethingElse");
 494         } catch (DateTimeParseException ex) {
 495             assertEquals(ex.getMessage().contains("ONE30SomethingElse"), true);
 496             assertEquals(ex.getParsedString(), "ONE30SomethingElse");
 497             assertEquals(ex.getErrorIndex(), 5);
 498             throw ex;
 499         }
 500     }
 501 
 502     @Test(expectedExceptions=NullPointerException.class)
 503     public void test_parseToBuilder_String_null() throws Exception {
 504         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 505         test.parseToBuilder((String) null);
 506     }
 507 
 508     //-----------------------------------------------------------------------
 509     @Test
 510     public void test_parseToBuilder_StringParsePosition() throws Exception {
 511         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 512         ParsePosition pos = new ParsePosition(0);
 513         DateTimeBuilder result = test.parseToBuilder("ONE30XXX", pos);
 514         assertEquals(pos.getIndex(), 5);

 515         assertEquals(pos.getErrorIndex(), -1);
 516         assertEquals(result.getFieldValueMap().size(), 1);
 517         assertEquals(result.getFieldValueMap().get(DAY_OF_MONTH), Long.valueOf(30));
 518     }
 519 
 520     @Test
 521     public void test_parseToBuilder_StringParsePosition_parseError() throws Exception {
 522         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 523         ParsePosition pos = new ParsePosition(0);
 524         DateTimeBuilder result = test.parseToBuilder("ONEXXX", pos);
 525         assertEquals(pos.getIndex(), 0);  // TODO: is this right?
 526         assertEquals(pos.getErrorIndex(), 3);

 527         assertEquals(result, null);
 528     }
 529 
 530     @Test(expectedExceptions=NullPointerException.class)
 531     public void test_parseToBuilder_StringParsePosition_nullString() throws Exception {
 532         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 533         ParsePosition pos = new ParsePosition(0);
 534         test.parseToBuilder((String) null, pos);
 535     }
 536 
 537     @Test(expectedExceptions=NullPointerException.class)
 538     public void test_parseToBuilder_StringParsePosition_nullParsePosition() throws Exception {
 539         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 540         test.parseToBuilder("ONE30", (ParsePosition) null);
 541     }
 542 
 543     @Test(expectedExceptions=IndexOutOfBoundsException.class)
 544     public void test_parseToBuilder_StringParsePosition_invalidPosition() throws Exception {
 545         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 546         ParsePosition pos = new ParsePosition(6);
 547         test.parseToBuilder("ONE30", pos);
 548     }
 549 
 550     //-----------------------------------------------------------------------
 551     //-----------------------------------------------------------------------
 552     @Test
 553     public void test_toFormat_format() throws Exception {
 554         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 555         Format format = test.toFormat();
 556         String result = format.format(LocalDate.of(2008, 6, 30));
 557         assertEquals(result, "ONE30");
 558     }
 559 
 560     @Test(expectedExceptions=NullPointerException.class)
 561     public void test_toFormat_format_null() throws Exception {
 562         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 563         Format format = test.toFormat();
 564         format.format(null);
 565     }
 566 
 567     @Test(expectedExceptions=IllegalArgumentException.class)
 568     public void test_toFormat_format_notTemporal() throws Exception {
 569         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 570         Format format = test.toFormat();
 571         format.format("Not a Temporal");
 572     }
 573 
 574     //-----------------------------------------------------------------------
 575     @Test
 576     public void test_toFormat_parseObject_String() throws Exception {
 577         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 578         Format format = test.toFormat();
 579         DateTimeBuilder result = (DateTimeBuilder) format.parseObject("ONE30");
 580         assertEquals(result.getFieldValueMap().size(), 1);
 581         assertEquals(result.getFieldValue(DAY_OF_MONTH), 30L);
 582     }
 583 
 584     @Test(expectedExceptions=ParseException.class)
 585     public void test_toFormat_parseObject_String_parseError() throws Exception {
 586         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 587         Format format = test.toFormat();
 588         try {
 589             format.parseObject("ONEXXX");
 590         } catch (ParseException ex) {
 591             assertEquals(ex.getMessage().contains("ONEXXX"), true);
 592             assertEquals(ex.getErrorOffset(), 3);
 593             throw ex;
 594         }
 595     }
 596 
 597     @Test(expectedExceptions=ParseException.class)
 598     public void test_toFormat_parseObject_String_parseErrorLongText() throws Exception {
 599         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 600         Format format = test.toFormat();
 601         try {


 604             assertEquals(ex.getMessage().contains("ONEXXX6789012345678901234567890123456789012345678901234567890123..."), true);
 605             assertEquals(ex.getParsedString(), "ONEXXX67890123456789012345678901234567890123456789012345678901234567890123456789");
 606             assertEquals(ex.getErrorIndex(), 3);
 607             throw ex;
 608         }
 609     }
 610 
 611     @Test(expectedExceptions=NullPointerException.class)
 612     public void test_toFormat_parseObject_String_null() throws Exception {
 613         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 614         Format format = test.toFormat();
 615         format.parseObject((String) null);
 616     }
 617 
 618     //-----------------------------------------------------------------------
 619     @Test
 620     public void test_toFormat_parseObject_StringParsePosition() throws Exception {
 621         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 622         Format format = test.toFormat();
 623         ParsePosition pos = new ParsePosition(0);
 624         DateTimeBuilder result = (DateTimeBuilder) format.parseObject("ONE30XXX", pos);
 625         assertEquals(pos.getIndex(), 5);
 626         assertEquals(pos.getErrorIndex(), -1);
 627         assertEquals(result.getFieldValueMap().size(), 1);
 628         assertEquals(result.getFieldValue(DAY_OF_MONTH), 30L);
 629     }
 630 
 631     @Test
 632     public void test_toFormat_parseObject_StringParsePosition_parseError() throws Exception {
 633         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 634         Format format = test.toFormat();
 635         ParsePosition pos = new ParsePosition(0);
 636         TemporalAccessor result = (TemporalAccessor) format.parseObject("ONEXXX", pos);
 637         assertEquals(pos.getIndex(), 0);  // TODO: is this right?
 638         assertEquals(pos.getErrorIndex(), 3);
 639         assertEquals(result, null);
 640     }
 641 
 642     @Test(expectedExceptions=NullPointerException.class)
 643     public void test_toFormat_parseObject_StringParsePosition_nullString() throws Exception {
 644         // SimpleDateFormat has this behavior
 645         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 646         Format format = test.toFormat();
 647         ParsePosition pos = new ParsePosition(0);
 648         format.parseObject((String) null, pos);




  44  *  * Neither the name of JSR-310 nor the names of its contributors
  45  *    may be used to endorse or promote products derived from this software
  46  *    without specific prior written permission.
  47  *
  48  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
  49  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
  50  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
  51  * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
  52  * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
  53  * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
  54  * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
  55  * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
  56  * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
  57  * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
  58  * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  59  */
  60 package tck.java.time.format;
  61 
  62 import static java.time.temporal.ChronoField.DAY_OF_MONTH;
  63 import static java.time.temporal.ChronoField.HOUR_OF_DAY;
  64 import static java.time.temporal.ChronoField.MONTH_OF_YEAR;
  65 import static java.time.temporal.ChronoField.YEAR;
  66 import static org.testng.Assert.assertEquals;
  67 import static org.testng.Assert.assertNull;
  68 import static org.testng.Assert.assertTrue;
  69 import static org.testng.Assert.fail;
  70 

  71 import java.text.Format;
  72 import java.text.ParseException;
  73 import java.text.ParsePosition;
  74 import java.util.Locale;
  75 
  76 import java.time.DateTimeException;
  77 import java.time.Instant;
  78 import java.time.LocalDate;
  79 import java.time.LocalDateTime;
  80 import java.time.LocalTime;
  81 import java.time.ZoneId;
  82 import java.time.ZoneOffset;
  83 import java.time.ZonedDateTime;
  84 import java.time.chrono.ThaiBuddhistChronology;
  85 import java.time.format.DateTimeFormatSymbols;
  86 import java.time.format.DateTimeFormatter;
  87 import java.time.format.DateTimeFormatterBuilder;

  88 import java.time.format.DateTimeParseException;

  89 import java.time.format.SignStyle;
  90 import java.time.chrono.Chronology;
  91 import java.time.chrono.IsoChronology;
  92 import java.time.OffsetDateTime;
  93 import java.time.OffsetTime;


  94 import java.time.temporal.Temporal;
  95 import java.time.temporal.TemporalAccessor;
  96 import java.time.temporal.TemporalQuery;
  97 
  98 import org.testng.annotations.BeforeMethod;
  99 import org.testng.annotations.DataProvider;
 100 import org.testng.annotations.Test;

 101 
 102 /**
 103  * Test DateTimeFormatter.
 104  */
 105 @Test(groups={"tck"})
 106 public class TCKDateTimeFormatter {
 107 
 108     private static final ZoneOffset OFFSET_PONE = ZoneOffset.ofHours(1);
 109     private static final ZoneOffset OFFSET_PTHREE = ZoneOffset.ofHours(3);
 110     private static final ZoneId ZONE_PARIS = ZoneId.of("Europe/Paris");
 111 
 112     private static final DateTimeFormatter BASIC_FORMATTER = DateTimeFormatter.ofPattern("'ONE'd");
 113     private static final DateTimeFormatter DATE_FORMATTER = DateTimeFormatter.ofPattern("'ONE'yyyy MM dd");
 114 
 115     private DateTimeFormatter fmt;
 116 
 117     @BeforeMethod
 118     public void setUp() {
 119         fmt = new DateTimeFormatterBuilder().appendLiteral("ONE")
 120                                             .appendValue(DAY_OF_MONTH, 1, 2, SignStyle.NOT_NEGATIVE)
 121                                             .toFormatter();
 122     }
 123 
 124     //-----------------------------------------------------------------------
 125     @Test
 126     public void test_withLocale() {
 127         DateTimeFormatter base = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 128         DateTimeFormatter test = base.withLocale(Locale.GERMAN);
 129         assertEquals(test.getLocale(), Locale.GERMAN);
 130     }
 131 
 132     @Test(expectedExceptions=NullPointerException.class)
 133     public void test_withLocale_null() {
 134         DateTimeFormatter base = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 135         base.withLocale((Locale) null);
 136     }
 137 
 138     //-----------------------------------------------------------------------
 139     @Test
 140     public void test_withChronology() {
 141         DateTimeFormatter test = fmt;
 142         assertEquals(test.getChronology(), null);
 143         test = test.withChronology(IsoChronology.INSTANCE);
 144         assertEquals(test.getChronology(), IsoChronology.INSTANCE);
 145         test = test.withChronology(null);
 146         assertEquals(test.getChronology(), null);
 147     }
 148 
 149     //-----------------------------------------------------------------------
 150     @Test
 151     public void test_withZone() {
 152         DateTimeFormatter test = fmt;
 153         assertEquals(test.getZone(), null);
 154         test = test.withZone(ZoneId.of("Europe/Paris"));
 155         assertEquals(test.getZone(), ZoneId.of("Europe/Paris"));
 156         test = test.withZone(ZoneOffset.UTC);
 157         assertEquals(test.getZone(), ZoneOffset.UTC);
 158         test = test.withZone(null);
 159         assertEquals(test.getZone(), null);
 160     }
 161 
 162     //-----------------------------------------------------------------------
 163     // print
 164     //-----------------------------------------------------------------------
 165     @DataProvider(name="print")
 166     Object[][] data_format() {
 167         LocalDate ld = LocalDate.of(2008, 6, 30);
 168         LocalTime lt = LocalTime.of(11, 30);
 169         LocalDateTime ldt = LocalDateTime.of(2008, 6, 30, 11, 30);

 170         OffsetTime ot = OffsetTime.of(LocalTime.of(11, 30), OFFSET_PONE);
 171         OffsetDateTime odt = OffsetDateTime.of(LocalDateTime.of(2008, 6, 30, 11, 30), OFFSET_PONE);
 172         ZonedDateTime zdt = ZonedDateTime.of(LocalDateTime.of(2008, 6, 30, 11, 30), ZONE_PARIS);
 173         Instant instant = Instant.ofEpochSecond(3600);
 174         return new Object[][] {
 175                 {null, null, ld, "2008::"},
 176                 {null, null, lt, ":11:"},
 177                 {null, null, ldt, "2008:11:"},

 178                 {null, null, ot, ":11:+01:00"},
 179                 {null, null, odt, "2008:11:+01:00"},
 180                 {null, null, zdt, "2008:11:+02:00Europe/Paris"},
 181                 {null, null, instant, "::"},
 182 
 183                 {null, ZONE_PARIS, ld, "2008::"},
 184                 {null, ZONE_PARIS, lt, ":11:"},
 185                 {null, ZONE_PARIS, ldt, "2008:11:"},

 186                 {null, ZONE_PARIS, ot, ":11:+01:00"},
 187                 {null, ZONE_PARIS, odt, "2008:12:+02:00Europe/Paris"},
 188                 {null, ZONE_PARIS, zdt, "2008:11:+02:00Europe/Paris"},
 189                 {null, ZONE_PARIS, instant, "1970:02:+01:00Europe/Paris"},
 190 
 191                 {null, OFFSET_PTHREE, ld, "2008::"},
 192                 {null, OFFSET_PTHREE, lt, ":11:"},
 193                 {null, OFFSET_PTHREE, ldt, "2008:11:"},

 194                 {null, OFFSET_PTHREE, ot, ":11:+01:00"},
 195                 {null, OFFSET_PTHREE, odt, "2008:13:+03:00"},
 196                 {null, OFFSET_PTHREE, zdt, "2008:12:+03:00"},
 197                 {null, OFFSET_PTHREE, instant, "1970:04:+03:00"},
 198 
 199                 {ThaiBuddhistChronology.INSTANCE, null, ld, "2551::"},
 200                 {ThaiBuddhistChronology.INSTANCE, null, lt, ":11:"},
 201                 {ThaiBuddhistChronology.INSTANCE, null, ldt, "2551:11:"},
 202                 {ThaiBuddhistChronology.INSTANCE, null, ot, ":11:+01:00"},
 203                 {ThaiBuddhistChronology.INSTANCE, null, odt, "2551:11:+01:00"},
 204                 {ThaiBuddhistChronology.INSTANCE, null, zdt, "2551:11:+02:00Europe/Paris"},
 205                 {ThaiBuddhistChronology.INSTANCE, null, instant, "::"},
 206 
 207                 {ThaiBuddhistChronology.INSTANCE, ZONE_PARIS, ld, "2551::"},
 208                 {ThaiBuddhistChronology.INSTANCE, ZONE_PARIS, lt, ":11:"},
 209                 {ThaiBuddhistChronology.INSTANCE, ZONE_PARIS, ldt, "2551:11:"},
 210                 {ThaiBuddhistChronology.INSTANCE, ZONE_PARIS, ot, ":11:+01:00"},
 211                 {ThaiBuddhistChronology.INSTANCE, ZONE_PARIS, odt, "2551:12:+02:00Europe/Paris"},
 212                 {ThaiBuddhistChronology.INSTANCE, ZONE_PARIS, zdt, "2551:11:+02:00Europe/Paris"},
 213                 {ThaiBuddhistChronology.INSTANCE, ZONE_PARIS, instant, "1970:02:+01:00Europe/Paris"},


 214         };
 215     }
 216 
 217     @Test(dataProvider="print")
 218     public void test_print_Temporal(Chronology overrideChrono, ZoneId overrideZone, Temporal temporal, String expected) {
 219         DateTimeFormatter test = new DateTimeFormatterBuilder()
 220                 .optionalStart().appendValue(YEAR, 4).optionalEnd()
 221                 .appendLiteral(':').optionalStart().appendValue(HOUR_OF_DAY, 2).optionalEnd()
 222                 .appendLiteral(':').optionalStart().appendOffsetId().optionalStart().appendZoneRegionId().optionalEnd().optionalEnd()
 223                 .toFormatter(Locale.ENGLISH)
 224                 .withChronology(overrideChrono).withZone(overrideZone);
 225         String result = test.format(temporal);
 226         assertEquals(result, expected);
 227     }
 228 
 229     @Test
 230     public void test_print_Temporal_simple() throws Exception {
 231         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 232         String result = test.format(LocalDate.of(2008, 6, 30));
 233         assertEquals(result, "ONE30");
 234     }
 235 
 236     @Test(expectedExceptions=DateTimeException.class)
 237     public void test_print_Temporal_noSuchField() throws Exception {
 238         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 239         test.format(LocalTime.of(11, 30));
 240     }
 241 
 242     @Test(expectedExceptions=NullPointerException.class)
 243     public void test_print_Temporal_null() throws Exception {
 244         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 245         test.format((TemporalAccessor) null);
 246     }
 247 
 248     //-----------------------------------------------------------------------
 249     @Test
 250     public void test_print_TemporalAppendable() throws Exception {
 251         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 252         StringBuilder buf = new StringBuilder();
 253         test.formatTo(LocalDate.of(2008, 6, 30), buf);
 254         assertEquals(buf.toString(), "ONE30");
 255     }
 256 
 257     @Test(expectedExceptions=DateTimeException.class)
 258     public void test_print_TemporalAppendable_noSuchField() throws Exception {
 259         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 260         StringBuilder buf = new StringBuilder();
 261         test.formatTo(LocalTime.of(11, 30), buf);
 262     }
 263 
 264     @Test(expectedExceptions=NullPointerException.class)
 265     public void test_print_TemporalAppendable_nullTemporal() throws Exception {
 266         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 267         StringBuilder buf = new StringBuilder();
 268         test.formatTo((TemporalAccessor) null, buf);
 269     }
 270 
 271     @Test(expectedExceptions=NullPointerException.class)
 272     public void test_print_TemporalAppendable_nullAppendable() throws Exception {
 273         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 274         test.formatTo(LocalDate.of(2008, 6, 30), (Appendable) null);
 275     }
 276 
 277     //-----------------------------------------------------------------------
 278     // parse(CharSequence)
 279     //-----------------------------------------------------------------------
 280     @Test
 281     public void test_parse_CharSequence() {
 282         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 283         TemporalAccessor result = test.parse("ONE30");
 284         assertEquals(result.isSupported(DAY_OF_MONTH), true);
 285         assertEquals(result.getLong(DAY_OF_MONTH), 30L);
 286         assertEquals(result.isSupported(HOUR_OF_DAY), false);
 287     }
 288 
 289     @Test
 290     public void test_parse_CharSequence_resolved() {
 291         DateTimeFormatter test = DateTimeFormatter.ISO_DATE;
 292         TemporalAccessor result = test.parse("2012-06-30");
 293         assertEquals(result.isSupported(YEAR), true);
 294         assertEquals(result.isSupported(MONTH_OF_YEAR), true);
 295         assertEquals(result.isSupported(DAY_OF_MONTH), true);
 296         assertEquals(result.isSupported(HOUR_OF_DAY), false);
 297         assertEquals(result.getLong(YEAR), 2012L);
 298         assertEquals(result.getLong(MONTH_OF_YEAR), 6L);
 299         assertEquals(result.getLong(DAY_OF_MONTH), 30L);
 300         assertEquals(result.query(LocalDate::from), LocalDate.of(2012, 6, 30));
 301     }
 302 
 303     @Test(expectedExceptions=NullPointerException.class)
 304     public void test_parse_CharSequence_null() {
 305         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 306         test.parse((String) null);
 307     }
 308 
 309     //-----------------------------------------------------------------------
 310     // parse(CharSequence)
 311     //-----------------------------------------------------------------------
 312     @Test
 313     public void test_parse_CharSequence_ParsePosition() {
 314         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 315         ParsePosition pos = new ParsePosition(3);
 316         TemporalAccessor result = test.parse("XXXONE30XXX", pos);
 317         assertEquals(pos.getIndex(), 8);
 318         assertEquals(pos.getErrorIndex(), -1);
 319         assertEquals(result.isSupported(DAY_OF_MONTH), true);
 320         assertEquals(result.getLong(DAY_OF_MONTH), 30L);
 321         assertEquals(result.isSupported(HOUR_OF_DAY), false);
 322     }
 323 
 324     @Test
 325     public void test_parse_CharSequence_ParsePosition_resolved() {
 326         DateTimeFormatter test = DateTimeFormatter.ISO_DATE;
 327         ParsePosition pos = new ParsePosition(3);
 328         TemporalAccessor result = test.parse("XXX2012-06-30XXX", pos);
 329         assertEquals(pos.getIndex(), 13);
 330         assertEquals(pos.getErrorIndex(), -1);
 331         assertEquals(result.isSupported(YEAR), true);
 332         assertEquals(result.isSupported(MONTH_OF_YEAR), true);
 333         assertEquals(result.isSupported(DAY_OF_MONTH), true);
 334         assertEquals(result.isSupported(HOUR_OF_DAY), false);
 335         assertEquals(result.getLong(YEAR), 2012L);
 336         assertEquals(result.getLong(MONTH_OF_YEAR), 6L);
 337         assertEquals(result.getLong(DAY_OF_MONTH), 30L);
 338         assertEquals(result.query(LocalDate::from), LocalDate.of(2012, 6, 30));
 339     }
 340 
 341     @Test(expectedExceptions=DateTimeParseException.class)
 342     public void test_parse_CharSequence_ParsePosition_parseError() {
 343         DateTimeFormatter test = DateTimeFormatter.ISO_DATE;
 344         ParsePosition pos = new ParsePosition(3);
 345         try {
 346             test.parse("XXX2012XXX", pos);
 347             fail();
 348         } catch (DateTimeParseException ex) {
 349             assertEquals(ex.getErrorIndex(), 7);
 350             throw ex;
 351         }
 352     }
 353 
 354     @Test(expectedExceptions=IndexOutOfBoundsException.class)
 355     public void test_parse_CharSequence_ParsePosition_indexTooBig() {
 356         DateTimeFormatter test = DateTimeFormatter.ISO_DATE;
 357         test.parse("Text", new ParsePosition(5));
 358     }
 359 
 360     @Test(expectedExceptions=NullPointerException.class)
 361     public void test_parse_CharSequence_ParsePosition_nullText() {
 362         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 363         test.parse((CharSequence) null, new ParsePosition(0));
 364     }
 365 
 366     @Test(expectedExceptions=NullPointerException.class)
 367     public void test_parse_CharSequence_ParsePosition_nullParsePosition() {
 368         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 369         test.parse("Text", (ParsePosition) null);
 370     }
 371 
 372     //-----------------------------------------------------------------------
 373     // parse(Query)
 374     //-----------------------------------------------------------------------
 375     @Test
 376     public void test_parse_Query_String() throws Exception {
 377         LocalDate result = DATE_FORMATTER.parse("ONE2012 07 27", LocalDate::from);
 378         assertEquals(result, LocalDate.of(2012, 7, 27));
 379     }
 380 
 381     @Test
 382     public void test_parse_Query_CharSequence() throws Exception {
 383         LocalDate result = DATE_FORMATTER.parse(new StringBuilder("ONE2012 07 27"), LocalDate::from);
 384         assertEquals(result, LocalDate.of(2012, 7, 27));
 385     }
 386 
 387     @Test(expectedExceptions=DateTimeParseException.class)
 388     public void test_parse_Query_String_parseError() throws Exception {
 389         try {


 420             assertEquals(ex.getParsedString(), "ONE2012 07 27SomethingElse");
 421             assertEquals(ex.getErrorIndex(), 13);
 422             throw ex;
 423         }
 424     }
 425 
 426     @Test(expectedExceptions=NullPointerException.class)
 427     public void test_parse_Query_String_nullText() throws Exception {
 428         DATE_FORMATTER.parse((String) null, LocalDate::from);
 429     }
 430 
 431     @Test(expectedExceptions=NullPointerException.class)
 432     public void test_parse_Query_String_nullRule() throws Exception {
 433         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 434         test.parse("30", (TemporalQuery<?>) null);
 435     }
 436 
 437     //-----------------------------------------------------------------------
 438     @Test
 439     public void test_parseBest_firstOption() throws Exception {
 440         DateTimeFormatter test = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm[XXX]");
 441         TemporalAccessor result = test.parseBest("2011-06-30 12:30+03:00", ZonedDateTime::from, LocalDateTime::from);
 442         LocalDateTime ldt = LocalDateTime.of(2011, 6, 30, 12, 30);
 443         assertEquals(result, ZonedDateTime.of(ldt, ZoneOffset.ofHours(3)));
 444     }
 445 
 446     @Test
 447     public void test_parseBest_secondOption() throws Exception {
 448         DateTimeFormatter test = DateTimeFormatter.ofPattern("yyyy-MM-dd[ HH:mm[XXX]]");
 449         TemporalAccessor result = test.parseBest("2011-06-30", ZonedDateTime::from, LocalDate::from);
 450         assertEquals(result, LocalDate.of(2011, 6, 30));
 451     }
 452 
 453     @Test(expectedExceptions=DateTimeParseException.class)
 454     public void test_parseBest_String_parseError() throws Exception {
 455         DateTimeFormatter test = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm[XXX]");
 456         try {
 457             test.parseBest("2011-06-XX", ZonedDateTime::from, LocalDateTime::from);
 458         } catch (DateTimeParseException ex) {
 459             assertEquals(ex.getMessage().contains("could not be parsed"), true);
 460             assertEquals(ex.getMessage().contains("XX"), true);
 461             assertEquals(ex.getParsedString(), "2011-06-XX");
 462             assertEquals(ex.getErrorIndex(), 8);
 463             throw ex;
 464         }
 465     }
 466 
 467     @Test(expectedExceptions=DateTimeParseException.class)
 468     public void test_parseBest_String_parseErrorLongText() throws Exception {
 469         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 470         try {
 471             test.parseBest("ONEXXX67890123456789012345678901234567890123456789012345678901234567890123456789", ZonedDateTime::from, LocalDate::from);
 472         } catch (DateTimeParseException ex) {
 473             assertEquals(ex.getMessage().contains("could not be parsed"), true);
 474             assertEquals(ex.getMessage().contains("ONEXXX6789012345678901234567890123456789012345678901234567890123..."), true);
 475             assertEquals(ex.getParsedString(), "ONEXXX67890123456789012345678901234567890123456789012345678901234567890123456789");
 476             assertEquals(ex.getErrorIndex(), 3);
 477             throw ex;
 478         }
 479     }
 480 
 481     @Test(expectedExceptions=DateTimeParseException.class)
 482     public void test_parseBest_String_parseIncomplete() throws Exception {
 483         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 484         try {
 485             test.parseBest("ONE30SomethingElse", ZonedDateTime::from, LocalDate::from);
 486         } catch (DateTimeParseException ex) {
 487             assertEquals(ex.getMessage().contains("could not be parsed"), true);
 488             assertEquals(ex.getMessage().contains("ONE30SomethingElse"), true);
 489             assertEquals(ex.getParsedString(), "ONE30SomethingElse");
 490             assertEquals(ex.getErrorIndex(), 5);
 491             throw ex;
 492         }
 493     }
 494 
 495     @Test(expectedExceptions=NullPointerException.class)
 496     public void test_parseBest_String_nullText() throws Exception {
 497         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 498         test.parseBest((String) null, ZonedDateTime::from, LocalDate::from);
 499     }
 500 
 501     @Test(expectedExceptions=NullPointerException.class)
 502     public void test_parseBest_String_nullRules() throws Exception {
 503         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 504         test.parseBest("30", (TemporalQuery<?>[]) null);
 505     }
 506 
 507     @Test(expectedExceptions=IllegalArgumentException.class)
 508     public void test_parseBest_String_zeroRules() throws Exception {
 509         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 510         test.parseBest("30", new TemporalQuery<?>[0]);
 511     }
 512 
 513     @Test(expectedExceptions=IllegalArgumentException.class)
 514     public void test_parseBest_String_oneRule() throws Exception {
 515         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 516         test.parseBest("30", LocalDate::from);
 517     }
 518 
 519     //-----------------------------------------------------------------------
 520     @Test
 521     public void test_parseUnresolved_StringParsePosition() {
 522         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 523         ParsePosition pos = new ParsePosition(0);
 524         TemporalAccessor result = test.parseUnresolved("ONE30XXX", pos);
 525         assertEquals(pos.getIndex(), 5);
 526         assertEquals(pos.getErrorIndex(), -1);
 527         assertEquals(result.getLong(DAY_OF_MONTH), 30L);
 528     }
 529 
 530     @Test
 531     public void test_parseUnresolved_StringParsePosition_parseError() {
 532         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 533         ParsePosition pos = new ParsePosition(0);
 534         TemporalAccessor result = test.parseUnresolved("ONEXXX", pos);
 535         assertEquals(pos.getIndex(), 0);
 536         assertEquals(pos.getErrorIndex(), 3);
 537         assertEquals(result, null);












































 538     }
 539 

 540     @Test
 541     public void test_parseUnresolved_StringParsePosition_duplicateFieldSameValue() {
 542         DateTimeFormatter test = new DateTimeFormatterBuilder()
 543                 .appendValue(MONTH_OF_YEAR).appendLiteral('-').appendValue(MONTH_OF_YEAR).toFormatter();
 544         ParsePosition pos = new ParsePosition(3);
 545         TemporalAccessor result = test.parseUnresolved("XXX6-6", pos);
 546         assertEquals(pos.getIndex(), 6);
 547         assertEquals(pos.getErrorIndex(), -1);
 548         assertEquals(result.getLong(MONTH_OF_YEAR), 6);

 549     }
 550 
 551     @Test
 552     public void test_parseUnresolved_StringParsePosition_duplicateFieldDifferentValue() {
 553         DateTimeFormatter test = new DateTimeFormatterBuilder()
 554                 .appendValue(MONTH_OF_YEAR).appendLiteral('-').appendValue(MONTH_OF_YEAR).toFormatter();
 555         ParsePosition pos = new ParsePosition(3);
 556         TemporalAccessor result = test.parseUnresolved("XXX6-7", pos);
 557         assertEquals(pos.getIndex(), 3);
 558         assertEquals(pos.getErrorIndex(), 5);
 559         assertEquals(result, null);
 560     }
 561 
 562     @Test(expectedExceptions=NullPointerException.class)
 563     public void test_parseUnresolved_StringParsePosition_nullString() {
 564         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 565         ParsePosition pos = new ParsePosition(0);
 566         test.parseUnresolved((String) null, pos);
 567     }
 568 
 569     @Test(expectedExceptions=NullPointerException.class)
 570     public void test_parseUnresolved_StringParsePosition_nullParsePosition() {
 571         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 572         test.parseUnresolved("ONE30", (ParsePosition) null);
 573     }
 574 
 575     @Test(expectedExceptions=IndexOutOfBoundsException.class)
 576     public void test_parseUnresolved_StringParsePosition_invalidPosition() {
 577         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 578         ParsePosition pos = new ParsePosition(6);
 579         test.parseUnresolved("ONE30", pos);
 580     }
 581 
 582     //-----------------------------------------------------------------------
 583     //-----------------------------------------------------------------------
 584     @Test
 585     public void test_toFormat_format() throws Exception {
 586         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 587         Format format = test.toFormat();
 588         String result = format.format(LocalDate.of(2008, 6, 30));
 589         assertEquals(result, "ONE30");
 590     }
 591 
 592     @Test(expectedExceptions=NullPointerException.class)
 593     public void test_toFormat_format_null() throws Exception {
 594         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 595         Format format = test.toFormat();
 596         format.format(null);
 597     }
 598 
 599     @Test(expectedExceptions=IllegalArgumentException.class)
 600     public void test_toFormat_format_notTemporal() throws Exception {
 601         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 602         Format format = test.toFormat();
 603         format.format("Not a Temporal");
 604     }
 605 
 606     //-----------------------------------------------------------------------
 607     @Test
 608     public void test_toFormat_parseObject_String() throws Exception {
 609         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 610         Format format = test.toFormat();
 611         TemporalAccessor result = (TemporalAccessor) format.parseObject("ONE30");
 612         assertEquals(result.isSupported(DAY_OF_MONTH), true);
 613         assertEquals(result.getLong(DAY_OF_MONTH), 30L);
 614     }
 615 
 616     @Test(expectedExceptions=ParseException.class)
 617     public void test_toFormat_parseObject_String_parseError() throws Exception {
 618         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 619         Format format = test.toFormat();
 620         try {
 621             format.parseObject("ONEXXX");
 622         } catch (ParseException ex) {
 623             assertEquals(ex.getMessage().contains("ONEXXX"), true);
 624             assertEquals(ex.getErrorOffset(), 3);
 625             throw ex;
 626         }
 627     }
 628 
 629     @Test(expectedExceptions=ParseException.class)
 630     public void test_toFormat_parseObject_String_parseErrorLongText() throws Exception {
 631         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 632         Format format = test.toFormat();
 633         try {


 636             assertEquals(ex.getMessage().contains("ONEXXX6789012345678901234567890123456789012345678901234567890123..."), true);
 637             assertEquals(ex.getParsedString(), "ONEXXX67890123456789012345678901234567890123456789012345678901234567890123456789");
 638             assertEquals(ex.getErrorIndex(), 3);
 639             throw ex;
 640         }
 641     }
 642 
 643     @Test(expectedExceptions=NullPointerException.class)
 644     public void test_toFormat_parseObject_String_null() throws Exception {
 645         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 646         Format format = test.toFormat();
 647         format.parseObject((String) null);
 648     }
 649 
 650     //-----------------------------------------------------------------------
 651     @Test
 652     public void test_toFormat_parseObject_StringParsePosition() throws Exception {
 653         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 654         Format format = test.toFormat();
 655         ParsePosition pos = new ParsePosition(0);
 656         TemporalAccessor result = (TemporalAccessor) format.parseObject("ONE30XXX", pos);
 657         assertEquals(pos.getIndex(), 5);
 658         assertEquals(pos.getErrorIndex(), -1);
 659         assertEquals(result.isSupported(DAY_OF_MONTH), true);
 660         assertEquals(result.getLong(DAY_OF_MONTH), 30L);
 661     }
 662 
 663     @Test
 664     public void test_toFormat_parseObject_StringParsePosition_parseError() throws Exception {
 665         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 666         Format format = test.toFormat();
 667         ParsePosition pos = new ParsePosition(0);
 668         TemporalAccessor result = (TemporalAccessor) format.parseObject("ONEXXX", pos);
 669         assertEquals(pos.getIndex(), 0);  // TODO: is this right?
 670         assertEquals(pos.getErrorIndex(), 3);
 671         assertEquals(result, null);
 672     }
 673 
 674     @Test(expectedExceptions=NullPointerException.class)
 675     public void test_toFormat_parseObject_StringParsePosition_nullString() throws Exception {
 676         // SimpleDateFormat has this behavior
 677         DateTimeFormatter test = fmt.withLocale(Locale.ENGLISH).withSymbols(DateTimeFormatSymbols.STANDARD);
 678         Format format = test.toFormat();
 679         ParsePosition pos = new ParsePosition(0);
 680         format.parseObject((String) null, pos);