001 /* 002 * JBoss, Home of Professional Open Source. 003 * Copyright 2008, Red Hat Middleware LLC, and individual contributors 004 * as indicated by the @author tags. See the copyright.txt file in the 005 * distribution for a full listing of individual contributors. 006 * 007 * This is free software; you can redistribute it and/or modify it 008 * under the terms of the GNU Lesser General Public License as 009 * published by the Free Software Foundation; either version 2.1 of 010 * the License, or (at your option) any later version. 011 * 012 * This software is distributed in the hope that it will be useful, 013 * but WITHOUT ANY WARRANTY; without even the implied warranty of 014 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 015 * Lesser General Public License for more details. 016 * 017 * You should have received a copy of the GNU Lesser General Public 018 * License along with this software; if not, write to the Free 019 * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 020 * 02110-1301 USA, or see the FSF site: http://www.fsf.org. 021 */ 022 package org.jboss.dna.graph.properties.basic; 023 024 import java.util.Calendar; 025 import java.util.Date; 026 import java.util.GregorianCalendar; 027 import java.util.Locale; 028 import java.util.concurrent.TimeUnit; 029 import net.jcip.annotations.Immutable; 030 import org.jboss.dna.common.util.CheckArg; 031 import org.joda.time.Chronology; 032 import org.joda.time.DateTime; 033 import org.joda.time.DateTimeZone; 034 035 /** 036 * Implementation of DateTime based upon the Joda-Time library. 037 * 038 * @author Randall Hauch 039 */ 040 @Immutable 041 public class JodaDateTime implements org.jboss.dna.graph.properties.DateTime { 042 043 /** 044 */ 045 private static final long serialVersionUID = -730188225988292422L; 046 047 private static final int MILLIS_IN_HOUR = 1000 * 60 * 60; 048 049 private final DateTime instance; 050 private transient String formattedString; 051 052 public JodaDateTime() { 053 this.instance = new DateTime(); 054 } 055 056 public JodaDateTime( String iso8601 ) { 057 this.instance = new DateTime(iso8601); 058 } 059 060 public JodaDateTime( String iso8601, 061 String timeZoneId ) { 062 this.instance = new DateTime(iso8601, DateTimeZone.forID(timeZoneId)); 063 } 064 065 public JodaDateTime( long milliseconds ) { 066 this.instance = new DateTime(milliseconds); 067 } 068 069 public JodaDateTime( long milliseconds, 070 Chronology chronology ) { 071 this.instance = new DateTime(milliseconds, chronology); 072 } 073 074 public JodaDateTime( long milliseconds, 075 String timeZoneId ) { 076 this.instance = new DateTime(milliseconds, DateTimeZone.forID(timeZoneId)); 077 } 078 079 public JodaDateTime( DateTimeZone dateTimeZone ) { 080 this.instance = new DateTime(dateTimeZone); 081 } 082 083 public JodaDateTime( int year, 084 int monthOfYear, 085 int dayOfMonth, 086 int hourOfDay, 087 int minuteOfHour, 088 int secondOfMinute, 089 int millisecondsOfSecond ) { 090 this.instance = new DateTime(year, monthOfYear, dayOfMonth, hourOfDay, minuteOfHour, secondOfMinute, millisecondsOfSecond); 091 } 092 093 public JodaDateTime( int year, 094 int monthOfYear, 095 int dayOfMonth, 096 int hourOfDay, 097 int minuteOfHour, 098 int secondOfMinute, 099 int millisecondsOfSecond, 100 Chronology chronology ) { 101 this.instance = new DateTime(year, monthOfYear, dayOfMonth, hourOfDay, minuteOfHour, secondOfMinute, 102 millisecondsOfSecond, chronology); 103 } 104 105 public JodaDateTime( int year, 106 int monthOfYear, 107 int dayOfMonth, 108 int hourOfDay, 109 int minuteOfHour, 110 int secondOfMinute, 111 int millisecondsOfSecond, 112 DateTimeZone dateTimeZone ) { 113 this.instance = new DateTime(year, monthOfYear, dayOfMonth, hourOfDay, minuteOfHour, secondOfMinute, 114 millisecondsOfSecond, dateTimeZone); 115 } 116 117 public JodaDateTime( int year, 118 int monthOfYear, 119 int dayOfMonth, 120 int hourOfDay, 121 int minuteOfHour, 122 int secondOfMinute, 123 int millisecondsOfSecond, 124 int timeZoneOffsetHours ) { 125 this.instance = new DateTime(year, monthOfYear, dayOfMonth, hourOfDay, minuteOfHour, secondOfMinute, 126 millisecondsOfSecond, DateTimeZone.forOffsetHours(timeZoneOffsetHours)); 127 } 128 129 public JodaDateTime( int year, 130 int monthOfYear, 131 int dayOfMonth, 132 int hourOfDay, 133 int minuteOfHour, 134 int secondOfMinute, 135 int millisecondsOfSecond, 136 String timeZoneId ) { 137 this.instance = new DateTime(year, monthOfYear, dayOfMonth, hourOfDay, minuteOfHour, secondOfMinute, 138 millisecondsOfSecond, DateTimeZone.forID(timeZoneId)); 139 } 140 141 public JodaDateTime( java.util.Date jdkDate ) { 142 this.instance = new DateTime(jdkDate); 143 } 144 145 public JodaDateTime( java.util.Calendar jdkCalendar ) { 146 this.instance = new DateTime(jdkCalendar); 147 } 148 149 public JodaDateTime( DateTime dateTime ) { 150 this.instance = dateTime; // it's immutable, so just hold onto the supplied instance 151 } 152 153 /** 154 * {@inheritDoc} 155 */ 156 public int getCenturyOfEra() { 157 return this.instance.getCenturyOfEra(); 158 } 159 160 /** 161 * {@inheritDoc} 162 */ 163 public int getDayOfMonth() { 164 return this.instance.getDayOfMonth(); 165 } 166 167 /** 168 * {@inheritDoc} 169 */ 170 public int getDayOfWeek() { 171 return this.instance.getDayOfWeek(); 172 } 173 174 /** 175 * {@inheritDoc} 176 */ 177 public int getDayOfYear() { 178 return this.instance.getDayOfYear(); 179 } 180 181 /** 182 * {@inheritDoc} 183 */ 184 public int getEra() { 185 return this.instance.getEra(); 186 } 187 188 /** 189 * {@inheritDoc} 190 */ 191 public int getHourOfDay() { 192 return this.instance.getHourOfDay(); 193 } 194 195 /** 196 * {@inheritDoc} 197 */ 198 public int getMillisOfSecond() { 199 return this.instance.getMillisOfSecond(); 200 } 201 202 /** 203 * {@inheritDoc} 204 */ 205 public long getMilliseconds() { 206 return this.instance.getMillis(); 207 } 208 209 /** 210 * {@inheritDoc} 211 */ 212 public int getMinuteOfHour() { 213 return this.instance.getMinuteOfHour(); 214 } 215 216 /** 217 * {@inheritDoc} 218 */ 219 public int getMonthOfYear() { 220 return this.instance.getMonthOfYear(); 221 } 222 223 /** 224 * {@inheritDoc} 225 */ 226 public int getSecondOfMinute() { 227 return this.instance.getSecondOfMinute(); 228 } 229 230 /** 231 * {@inheritDoc} 232 */ 233 public String getString() { 234 if (this.formattedString == null) { 235 // This is transient and can be done multiple times by concurrent threads (without locking), 236 // since the object is immutable 237 this.formattedString = this.instance.toString(org.joda.time.format.ISODateTimeFormat.dateTime()); 238 } 239 return this.formattedString; 240 } 241 242 /** 243 * {@inheritDoc} 244 */ 245 public int getWeekOfWeekyear() { 246 return this.instance.getWeekOfWeekyear(); 247 } 248 249 /** 250 * {@inheritDoc} 251 */ 252 public int getWeekyear() { 253 return this.instance.getWeekyear(); 254 } 255 256 /** 257 * {@inheritDoc} 258 */ 259 public int getYear() { 260 return this.instance.getYear(); 261 } 262 263 /** 264 * {@inheritDoc} 265 */ 266 public int getYearOfCentury() { 267 return this.instance.getYearOfCentury(); 268 } 269 270 /** 271 * {@inheritDoc} 272 */ 273 public int getYearOfEra() { 274 return this.instance.getYearOfEra(); 275 } 276 277 /** 278 * {@inheritDoc} 279 */ 280 public int getTimeZoneOffsetHours() { 281 // return this.instance.getZone().toTimeZone().getRawOffset() / MILLIS_IN_HOUR; 282 return this.instance.getZone().getOffset(this.instance.getMillis()) / MILLIS_IN_HOUR; 283 } 284 285 /** 286 * {@inheritDoc} 287 */ 288 public String getTimeZoneId() { 289 return this.instance.getZone().getID(); 290 } 291 292 /** 293 * {@inheritDoc} 294 */ 295 public Calendar toCalendar() { 296 return toCalendar(null); 297 } 298 299 /** 300 * {@inheritDoc} 301 */ 302 public Calendar toCalendar( Locale locale ) { 303 return this.instance.toCalendar(locale); 304 } 305 306 /** 307 * {@inheritDoc} 308 */ 309 public Date toDate() { 310 return this.instance.toDate(); 311 } 312 313 /** 314 * {@inheritDoc} 315 */ 316 public GregorianCalendar toGregorianCalendar() { 317 return this.instance.toGregorianCalendar(); 318 } 319 320 /** 321 * {@inheritDoc} 322 */ 323 public int compareTo( org.jboss.dna.graph.properties.DateTime that ) { 324 if (that instanceof JodaDateTime) { 325 return this.instance.compareTo(((JodaDateTime)that).instance); 326 } 327 long diff = this.toUtcTimeZone().getMilliseconds() - that.toUtcTimeZone().getMilliseconds(); 328 return (int)diff; 329 } 330 331 /** 332 * {@inheritDoc} 333 */ 334 @Override 335 public int hashCode() { 336 return this.instance.hashCode(); 337 } 338 339 /** 340 * {@inheritDoc} 341 */ 342 @Override 343 public boolean equals( Object obj ) { 344 if (obj == this) return true; 345 if (obj instanceof JodaDateTime) { 346 JodaDateTime that = (JodaDateTime)obj; 347 return this.instance.equals(that.instance); 348 } 349 if (obj instanceof DateTime) { 350 return this.instance.equals(obj); 351 } 352 return false; 353 } 354 355 /** 356 * {@inheritDoc} 357 */ 358 @Override 359 public String toString() { 360 return getString(); 361 } 362 363 /** 364 * {@inheritDoc} 365 */ 366 public org.jboss.dna.graph.properties.DateTime toUtcTimeZone() { 367 DateTime jodaTime = this.instance.withZone(DateTimeZone.forID("UTC")); 368 return new JodaDateTime(jodaTime); 369 } 370 371 /** 372 * {@inheritDoc} 373 */ 374 public org.jboss.dna.graph.properties.DateTime toTimeZone( String timeZoneId ) { 375 CheckArg.isNotNull(timeZoneId, "time zone identifier"); 376 DateTime jodaTime = this.instance.withZone(DateTimeZone.forID(timeZoneId)); 377 return new JodaDateTime(jodaTime); 378 } 379 380 /** 381 * {@inheritDoc} 382 * 383 * @see org.jboss.dna.graph.properties.DateTime#isBefore(org.jboss.dna.graph.properties.DateTime) 384 */ 385 public boolean isBefore( org.jboss.dna.graph.properties.DateTime other ) { 386 return this.compareTo(other) < 0; 387 } 388 389 /** 390 * {@inheritDoc} 391 * 392 * @see org.jboss.dna.graph.properties.DateTime#isSameAs(org.jboss.dna.graph.properties.DateTime) 393 */ 394 public boolean isSameAs( org.jboss.dna.graph.properties.DateTime other ) { 395 return this.compareTo(other) == 0; 396 } 397 398 /** 399 * {@inheritDoc} 400 * 401 * @see org.jboss.dna.graph.properties.DateTime#isAfter(org.jboss.dna.graph.properties.DateTime) 402 */ 403 public boolean isAfter( org.jboss.dna.graph.properties.DateTime other ) { 404 return this.compareTo(other) > 0; 405 } 406 407 /** 408 * {@inheritDoc} 409 * 410 * @see org.jboss.dna.graph.properties.DateTime#minus(long, java.util.concurrent.TimeUnit) 411 */ 412 public org.jboss.dna.graph.properties.DateTime minus( long timeAmount, 413 TimeUnit unit ) { 414 CheckArg.isNotNull(unit, "unit"); 415 return new JodaDateTime(this.instance.minus(TimeUnit.MILLISECONDS.convert(timeAmount, unit))); 416 } 417 418 /** 419 * {@inheritDoc} 420 * 421 * @see org.jboss.dna.graph.properties.DateTime#minusDays(int) 422 */ 423 public org.jboss.dna.graph.properties.DateTime minusDays( int days ) { 424 return new JodaDateTime(this.instance.minusDays(days)); 425 } 426 427 /** 428 * {@inheritDoc} 429 * 430 * @see org.jboss.dna.graph.properties.DateTime#minusHours(int) 431 */ 432 public org.jboss.dna.graph.properties.DateTime minusHours( int hours ) { 433 return new JodaDateTime(this.instance.minusHours(hours)); 434 } 435 436 /** 437 * {@inheritDoc} 438 * 439 * @see org.jboss.dna.graph.properties.DateTime#minusMillis(int) 440 */ 441 public org.jboss.dna.graph.properties.DateTime minusMillis( int milliseconds ) { 442 return new JodaDateTime(this.instance.minusMillis(milliseconds)); 443 } 444 445 /** 446 * {@inheritDoc} 447 * 448 * @see org.jboss.dna.graph.properties.DateTime#minusMinutes(int) 449 */ 450 public org.jboss.dna.graph.properties.DateTime minusMinutes( int minutes ) { 451 return new JodaDateTime(this.instance.minusMinutes(minutes)); 452 } 453 454 /** 455 * {@inheritDoc} 456 * 457 * @see org.jboss.dna.graph.properties.DateTime#minusMonths(int) 458 */ 459 public org.jboss.dna.graph.properties.DateTime minusMonths( int months ) { 460 return new JodaDateTime(this.instance.minusMonths(months)); 461 } 462 463 /** 464 * {@inheritDoc} 465 * 466 * @see org.jboss.dna.graph.properties.DateTime#minusSeconds(int) 467 */ 468 public org.jboss.dna.graph.properties.DateTime minusSeconds( int seconds ) { 469 return new JodaDateTime(this.instance.minusSeconds(seconds)); 470 } 471 472 /** 473 * {@inheritDoc} 474 * 475 * @see org.jboss.dna.graph.properties.DateTime#minusWeeks(int) 476 */ 477 public org.jboss.dna.graph.properties.DateTime minusWeeks( int weeks ) { 478 return new JodaDateTime(this.instance.minusWeeks(weeks)); 479 } 480 481 /** 482 * {@inheritDoc} 483 * 484 * @see org.jboss.dna.graph.properties.DateTime#minusYears(int) 485 */ 486 public org.jboss.dna.graph.properties.DateTime minusYears( int years ) { 487 return new JodaDateTime(this.instance.minusYears(years)); 488 } 489 490 /** 491 * {@inheritDoc} 492 * 493 * @see org.jboss.dna.graph.properties.DateTime#plus(long, java.util.concurrent.TimeUnit) 494 */ 495 public org.jboss.dna.graph.properties.DateTime plus( long timeAmount, 496 TimeUnit unit ) { 497 CheckArg.isNotNull(unit, "unit"); 498 return new JodaDateTime(this.instance.plus(TimeUnit.MILLISECONDS.convert(timeAmount, unit))); 499 } 500 501 /** 502 * {@inheritDoc} 503 * 504 * @see org.jboss.dna.graph.properties.DateTime#plusDays(int) 505 */ 506 public org.jboss.dna.graph.properties.DateTime plusDays( int days ) { 507 return new JodaDateTime(this.instance.plusDays(days)); 508 } 509 510 /** 511 * {@inheritDoc} 512 * 513 * @see org.jboss.dna.graph.properties.DateTime#plusHours(int) 514 */ 515 public org.jboss.dna.graph.properties.DateTime plusHours( int hours ) { 516 return new JodaDateTime(this.instance.plusHours(hours)); 517 } 518 519 /** 520 * {@inheritDoc} 521 * 522 * @see org.jboss.dna.graph.properties.DateTime#plusMillis(int) 523 */ 524 public org.jboss.dna.graph.properties.DateTime plusMillis( int milliseconds ) { 525 return new JodaDateTime(this.instance.plusMillis(milliseconds)); 526 } 527 528 /** 529 * {@inheritDoc} 530 * 531 * @see org.jboss.dna.graph.properties.DateTime#plusMinutes(int) 532 */ 533 public org.jboss.dna.graph.properties.DateTime plusMinutes( int minutes ) { 534 return new JodaDateTime(this.instance.plusMinutes(minutes)); 535 } 536 537 /** 538 * {@inheritDoc} 539 * 540 * @see org.jboss.dna.graph.properties.DateTime#plusMonths(int) 541 */ 542 public org.jboss.dna.graph.properties.DateTime plusMonths( int months ) { 543 return new JodaDateTime(this.instance.plusMonths(months)); 544 } 545 546 /** 547 * {@inheritDoc} 548 * 549 * @see org.jboss.dna.graph.properties.DateTime#plusSeconds(int) 550 */ 551 public org.jboss.dna.graph.properties.DateTime plusSeconds( int seconds ) { 552 return new JodaDateTime(this.instance.plusSeconds(seconds)); 553 } 554 555 /** 556 * {@inheritDoc} 557 * 558 * @see org.jboss.dna.graph.properties.DateTime#plusWeeks(int) 559 */ 560 public org.jboss.dna.graph.properties.DateTime plusWeeks( int weeks ) { 561 return new JodaDateTime(this.instance.plusWeeks(weeks)); 562 } 563 564 /** 565 * {@inheritDoc} 566 * 567 * @see org.jboss.dna.graph.properties.DateTime#plusYears(int) 568 */ 569 public org.jboss.dna.graph.properties.DateTime plusYears( int years ) { 570 return new JodaDateTime(this.instance.plusYears(years)); 571 } 572 573 }