I have a ISO 8601 date, lets say: 2012-01-19T19:00-05:00
My machine timezone is GMT+1
I\'m trying to use joda to parse this and convert
EDIT
https://stackoverflow.com/a/23242779/812919
Is a better solution.
For any future readers, if you are trying to parse a string in the format yyyyMMddTHHmmssZ. Its easier to parse it with the following code. Code is in Kotlin. The iCalendar recur rule is an example of where this format might appear.
// Reads from end to start to accommodate case where year has 4+ digits. 10100 for example.
fun iso8601GetPart(hashMap : HashMap,noOfCharsFromEnd : Int?) : String{
var str = hashMap.get("DATE_TIME")
var endIndex = str.length
if(str.get(str.length-1)=='T' || str.get(str.length-1)=='Z'){
endIndex--
}
if(noOfCharsFromEnd==null){
return str
}else{
hashMap.put("DATE_TIME", str.substring(0, endIndex - noOfCharsFromEnd))
return str.substring(endIndex-noOfCharsFromEnd,endIndex)
}
}
fun foo(){
var hashMap = HashMap<String,String>()
hashMap.put("DATE_TIME",dateTimeString)
var secOfMin = iso8601GetPart(hashMap,2).toInt()
var minOfHour = iso8601GetPart(hashMap,2).toInt()
var hourOfDay = iso8601GetPart(hashMap,2).toInt()
var dayOfMonth = iso8601GetPart(hashMap,2).toInt()
var monthOfYear = iso8601GetPart(hashMap,2).toInt()
var years = iso8601GetPart(hashMap,null).toInt()
}
The Joda-Time team has told us to migrate to the java.time framework built into Java 8 and later. The java.time framework is defined by JSR 310. Much of the java.time functionality has been back-ported to Java 6 & 7 and further adapted for Android.
The java.time classes include OffsetDateTime to represent a moment on the timeline with an offset-from-UTC but not a full time zone.
The java.time classes use the standard ISO 8601 formats by default when parsing or generating strings. So no need to define a formatting pattern.
String input = "2012-01-19T19:00-05:00";
OffsetDateTime odt = OffsetDateTime.parse( input );
A time zone is an offset plus rules for handling anomalies such as Daylight Saving Time (DST). A proper time zone name uses a continent/region format. You can assign a time zone (ZoneId) to an OffsetDateTime to get a ZonedDateTime.
ZoneId zoneId = ZoneId.of( "America/Montreal" );
ZonedDateTime zdt = odt.atZoneSameInstant( zoneId );
Here's a working groovy testcase. Shows how times in other timezones can be displayed.
import org.joda.time.*
import org.joda.time.format.*
@Grapes([
@Grab(group='joda-time', module='joda-time', version='1.6.2')
])
class JodaTimeTest extends GroovyTestCase {
void testTimeZone() {
DateTimeFormatter parser = ISODateTimeFormat.dateTimeParser()
DateTimeFormatter formatter = ISODateTimeFormat.dateTimeNoMillis()
DateTime dateTimeHere = parser.parseDateTime("2012-01-19T19:00:00-05:00")
DateTime dateTimeInLondon = dateTimeHere.withZone(DateTimeZone.forID("Europe/London"))
DateTime dateTimeInParis = dateTimeHere.withZone(DateTimeZone.forID("Europe/Paris"))
assertEquals("2012-01-20T00:00:00Z", formatter.print(dateTimeHere))
assertEquals("2012-01-20T00:00:00Z", formatter.print(dateTimeInLondon))
assertEquals("2012-01-20T01:00:00+01:00", formatter.print(dateTimeInParis))
}
}
Note: