DateTimeRule dtr;
AnnualTimeZoneRule atzr;
final int STARTYEAR = 2000;
InitialTimeZoneRule ir = new InitialTimeZoneRule(
"RBTZ_Initial", // Initial time Name
-1*HOUR, // Raw offset
1*HOUR); // DST saving amount
// RBTZ
RuleBasedTimeZone rbtz1 = new RuleBasedTimeZone("RBTZ1", ir);
dtr = new DateTimeRule(Calendar.SEPTEMBER, 30, Calendar.SATURDAY, false,
1*HOUR, DateTimeRule.WALL_TIME); // SUN<=30 in September, at 1AM wall time
atzr = new AnnualTimeZoneRule("RBTZ_DST1",
-1*HOUR /* rawOffset */, 1*HOUR /* dstSavings */, dtr,
STARTYEAR, AnnualTimeZoneRule.MAX_YEAR);
rbtz1.addTransitionRule(atzr);
dtr = new DateTimeRule(Calendar.FEBRUARY, 2, Calendar.SUNDAY,
1*HOUR, DateTimeRule.WALL_TIME); // 2nd Sunday in February, at 1AM wall time
atzr = new AnnualTimeZoneRule("RBTZ_STD1",
-1*HOUR /* rawOffset */, 0 /* dstSavings */, dtr,
STARTYEAR, AnnualTimeZoneRule.MAX_YEAR);
rbtz1.addTransitionRule(atzr);
// Equivalent, but different date rule type
RuleBasedTimeZone rbtz2 = new RuleBasedTimeZone("RBTZ2", ir);
dtr = new DateTimeRule(Calendar.SEPTEMBER, -1, Calendar.SATURDAY,
1*HOUR, DateTimeRule.WALL_TIME); // Last Sunday in September at 1AM wall time
atzr = new AnnualTimeZoneRule("RBTZ_DST2", -1*HOUR, 1*HOUR, dtr, STARTYEAR, AnnualTimeZoneRule.MAX_YEAR);
rbtz2.addTransitionRule(atzr);
dtr = new DateTimeRule(Calendar.FEBRUARY, 8, Calendar.SUNDAY, true,
1*HOUR, DateTimeRule.WALL_TIME); // SUN>=8 in February, at 1AM wall time
atzr = new AnnualTimeZoneRule("RBTZ_STD2", -1*HOUR, 0, dtr, STARTYEAR, AnnualTimeZoneRule.MAX_YEAR);
rbtz2.addTransitionRule(atzr);
// Equivalent, but different time rule type
RuleBasedTimeZone rbtz3 = new RuleBasedTimeZone("RBTZ3", ir);
dtr = new DateTimeRule(Calendar.SEPTEMBER, 30, Calendar.SATURDAY, false,
2*HOUR, DateTimeRule.UTC_TIME);
atzr = new AnnualTimeZoneRule("RBTZ_DST3", -1*HOUR, 1*HOUR, dtr, STARTYEAR, AnnualTimeZoneRule.MAX_YEAR);
rbtz3.addTransitionRule(atzr);
dtr = new DateTimeRule(Calendar.FEBRUARY, 2, Calendar.SUNDAY,
0*HOUR, DateTimeRule.STANDARD_TIME);
atzr = new AnnualTimeZoneRule("RBTZ_STD3", -1*HOUR, 0, dtr, STARTYEAR, AnnualTimeZoneRule.MAX_YEAR);
rbtz3.addTransitionRule(atzr);
// Check equivalency for 10 years
long start = getUTCMillis(STARTYEAR, Calendar.JANUARY, 1);
long until = getUTCMillis(STARTYEAR + 10, Calendar.JANUARY, 1);
if (!(stz.hasEquivalentTransitions(rbtz1, start, until))) {
errln("FAIL: rbtz1 must be equivalent to the SimpleTimeZone in the time range.");
}
if (!(stz.hasEquivalentTransitions(rbtz2, start, until))) {
errln("FAIL: rbtz2 must be equivalent to the SimpleTimeZone in the time range.");
}
if (!(stz.hasEquivalentTransitions(rbtz3, start, until))) {
errln("FAIL: rbtz3 must be equivalent to the SimpleTimeZone in the time range.");
}
// hasSameRules
if (rbtz1.hasSameRules(rbtz2)) {
errln("FAIL: rbtz1 and rbtz2 have different rules, but returned true.");
}
if (rbtz1.hasSameRules(rbtz3)) {
errln("FAIL: rbtz1 and rbtz3 have different rules, but returned true.");
}
RuleBasedTimeZone rbtz1c = (RuleBasedTimeZone)rbtz1.clone();
if (!rbtz1.hasSameRules(rbtz1c)) {
errln("FAIL: Cloned RuleBasedTimeZone must have the same rules with the original.");
}
// getOffset
GregorianCalendar cal = new GregorianCalendar();
int[] offsets = new int[2];
int offset;
boolean dst;
cal.setTimeZone(rbtz1);
cal.clear();
// Jan 1, 1000 BC
cal.set(Calendar.ERA, GregorianCalendar.BC);
cal.set(1000, Calendar.JANUARY, 1);
offset = rbtz1.getOffset(cal.get(Calendar.ERA), cal.get(Calendar.YEAR), cal.get(Calendar.MONTH),
cal.get(Calendar.DAY_OF_MONTH), cal.get(Calendar.DAY_OF_WEEK), cal.get(Calendar.MILLISECONDS_IN_DAY));
if (offset != 0) {
errln("FAIL: Invalid time zone offset: " + offset + " /expected: 0");
}
dst = rbtz1.inDaylightTime(cal.getTime());
if (!dst) {
errln("FAIL: Invalid daylight saving time");
}
rbtz1.getOffset(cal.getTimeInMillis(), true, offsets);
if (offsets[0] != -3600000) {
errln("FAIL: Invalid time zone raw offset: " + offsets[0] + " /expected: -3600000");
}
if (offsets[1] != 3600000) {
errln("FAIL: Invalid DST amount: " + offsets[1] + " /expected: 3600000");
}
// July 1, 2000, AD
cal.set(Calendar.ERA, GregorianCalendar.AD);
cal.set(2000, Calendar.JULY, 1);
offset = rbtz1.getOffset(cal.get(Calendar.ERA), cal.get(Calendar.YEAR), cal.get(Calendar.MONTH),
cal.get(Calendar.DAY_OF_MONTH), cal.get(Calendar.DAY_OF_WEEK), cal.get(Calendar.MILLISECONDS_IN_DAY));
if (offset != -3600000) {
errln("FAIL: Invalid time zone offset: " + offset + " /expected: -3600000");
}
dst = rbtz1.inDaylightTime(cal.getTime());
if (dst) {
errln("FAIL: Invalid daylight saving time");
}
rbtz1.getOffset(cal.getTimeInMillis(), true, offsets);
if (offsets[0] != -3600000) {
errln("FAIL: Invalid time zone raw offset: " + offsets[0] + " /expected: -3600000");
}
if (offsets[1] != 0) {
errln("FAIL: Invalid DST amount: " + offsets[1] + " /expected: 0");
}
// July 1, 2000, AD
// Try to add 3rd final rule
dtr = new DateTimeRule(Calendar.OCTOBER, 15, 1*HOUR, DateTimeRule.WALL_TIME);
atzr = new AnnualTimeZoneRule("3RD_ATZ", -1*HOUR, 2*HOUR, dtr, STARTYEAR, AnnualTimeZoneRule.MAX_YEAR);
boolean bException = false;
try {
rbtz1.addTransitionRule(atzr);
} catch (IllegalStateException ise) {
bException = true;
}
if (!bException) {
errln("FAIL: 3rd final rule must be rejected");
}
// Try to add an initial rule
bException = false;
try {
rbtz1.addTransitionRule(new InitialTimeZoneRule("Test Initial", 2*HOUR, 0));
} catch (IllegalArgumentException iae) {
bException = true;
}
if (!bException) {
errln("FAIL: InitialTimeZoneRule must be rejected");