I am trying to read a timestamp I have in my database mysql and save it to a Date variable in java.
I want it with this format: YYYY-MM-DD HH:MM:SS (24 hour format)
In my database I have a timestamp with that format but each time I try to get as timestamp I read 2014 and if I read it as Date with getDate()... I get "ago 16, 2014"
I'm not sure what you really want. Do you want to get a java.sql.Timestamp instance or do you want to get the timestamp as string with the mentioned pattern?
Maybe that helps:
ResultSet rs = ...
Timestamp t = rs.getTimestamp(...);
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
String str = sdf.format(t);
// get the timestamp from the DB
java.sql.Timestamp yourTimestamp = youNameItGetTimestamp();
// Create the corresponding Date object
java.util.Date date = new java.util.Date(yourTimestamp.getTime());
// show in a string
java.text.SimpleDateFormat formatter = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss");
java.lang.String printableDate = formatter.format(date);
System.out.println("here you have it: <" + printableDate + ">");
The other Answers are correct but use troublesome old legacy date-time classes. Instead use java.time classes.
Conversion
New methods have been added to the old classes to facilitate conversion such as java.sql.Timestamp::toInstant().
java.sql.Timestamp ts = myResultSet.getTimestamp( … ) ;
Instant instant = ts.toInstant();
Instant
The Instant class represents a moment on the timeline in UTC with a resolution of nanoseconds. Its toString method generates a String in one of the standard ISO 8601 formats.
String output = instant.toString();
2011-12-03T10:15:30Z
You could replace the T with a SPACE and delete the Z to get your format.
output = output.replace( "T" , " ").replace( "Z" , "" ) ;
2011-12-03 10:15:30
ZonedDateTime
If you want to see the same moment but through the lens of a particular time zone, generate a ZonedDateTime.
ZoneId zoneId = ZonedId.of( "America/Montreal" );
ZonedDateTime zdt = instant.atZone( zoneId );
Define a custom DateTimeFormatter object. Or use DateTimeFormatter.ISO_LOCAL_DATE_TIME and replace the T with a SPACE.
String output = zdt.format( DateTimeFormatter.ISO_LOCAL_DATE_TIME ).replace( "T" , " " );
2011-12-03 05:15:30
About java.time
The java.time framework is built into Java 8 and later. These classes supplant the troublesome old date-time classes such as java.util.Date, .Calendar, & java.text.SimpleDateFormat.
The Joda-Time project, now in maintenance mode, advises migration to java.time.
To learn more, see the Oracle Tutorial. And search Stack Overflow for many examples and explanations.
Much of the java.time functionality is back-ported to Java 6 & 7 in ThreeTen-Backport and further adapted to Android in ThreeTenABP (see How to use…).
The ThreeTen-Extra project extends java.time with additional classes. This project is a proving ground for possible future additions to java.time. You may find some useful classes here such as Interval, YearWeek, YearQuarter, and more.
have you tried some thing like this :
java.sql.Date timeStamp = new java.sql.Timestamp( object.getDate() );
also this link may help you :
http://dev.mysql.com/doc/refman/5.5/en/date-and-time-functions.html
What's the type of your field? Is it a string/varchar? How about using SimpleDateFormat?
i.e.
final Date myDate = new SimpleDateFormat(FORMAT_STRING).parse(value);
See SimpleDateFormat documentation for more details.
BTW: A litte code and database definition would have been nice...
Related
This question already has answers here:
Adding n hours to a date in Java?
(16 answers)
Closed 4 years ago.
How do i add hours to a date object. Below is my code:
String dateStart = timeStamp;
String dateStop = valueCon;
SimpleDateFormat format = new SimpleDateFormat("yy/MM/dd HH:mm:ss");
Date d1 = null;
Date d2 = null;
d1 = format.parse(dateStart);
d2 = format.parse(datestop);
I want to add 4 hours to d2 date object. How do i achieve it?
I tried to use :
Date modd1= new Date(d2+TimeUnit.MINUTES.toHours(240));
But it accepts only long object for adding. Thus failed.
Please support to solve this.Thanks in advance.
like others, i'd recommend using java.time if that's an option. the APIs are more consistent, and do a better job of catering to these types of operations.
however, to answer your question as-is... one option is to adjust the millisecond form of the Date instance by using get/setTime() as follows:
#Test
public void adjustTime() {
final Date date = new Date();
System.out.println("## Before adding four hours: " + date);
date.setTime(date.getTime() + TimeUnit.HOURS.toMillis(4));
System.out.println("## After adding four hours: " + date);
}
hope that helps!
If you are using java.time it can be more helpful :
LocalDateTime dateStart = LocalDateTime.now();
LocalDateTime dateStop = dateStart.plusHours(4);
To format the date you can use :
String d1 = dateStart.format(DateTimeFormatter.ofPattern("yy/MM/dd HH:mm:ss"));
String d2 = dateStop.format(DateTimeFormatter.ofPattern("yy/MM/dd HH:mm:ss"));
Well there are several ways to do
Using Calendar class
Calendar cal = Calendar.getInstance(); // creates calendar
cal.setTime(anyDateObject); // sets calendar time/date
cal.add(Calendar.HOUR_OF_DAY, 4); // adds four hour
Date date = cal.getTime(); // returns new date object
If you are using ApacheCOmmon Lang
Date newDate = DateUtils.addHours(oldDate, 3);
If you are using Joda-time
DateTime dt = new DateTime();
DateTime added = dt.plusHours(4);
and if you are using Java 8 best would be LocalDateTime
LocalDateTime startDate = LocalDateTime.now();
LocalDateTime stopdate = startDate.plusHours(4);
tl;dr
Never use Date or SimpleDateFormat classes.
Use only modern java.time classes.
Example code:
LocalDateTime.parse( // Parsing input string to an object without concept of zone or offset.
"18/01/23 12:34:56" , // Input lacking indicator of zone/offset.
DateTimeFormatter.ofPattern( "uu/MM/dd HH:mm:ss" ) // Define formatting pattern matching your input.
)
.plusHours( 4 ) // Add four hours. Generating a new `LocalDateTime` object, per immutable objects pattern.
.toString() // Generate a String in standard ISO 8601 format.
2018-01-23T16:34:56
java.time
The modern approach uses the java.time classes rather than the troublesome old legacy date-time classes. Never use Date, Calendar, SimpleDateFormat.
DateTimeFormatter f = DateTimeFormatter.ofPattern( "uu/MM/dd HH:mm:ss" ) ;
Unzoned
Apparently your input lacks an indicator of time zone or offset-from-UTC. So parse as a LocalDateTime.
LocalDateTime ldt = LocalDateTime.parse( "18/01/23 12:34:56" ) ;
ldt.toString(): 2018-01-23T12:34:56
A LocalDateTime has no concept of time zone or offset-from-UTC. So it does not represent an actual moment, and is not a point on the timeline. A LocalDateTime is only a rough idea about potential moments along a range of about 26-27 hours.
Zoned
If you know for certain the input data was intended to represent a moment in a particular zone, apply a ZoneId to produce a ZonedDateTime. A ZonedDateTime does represent an actual moment, a point on the timeline.
ZoneId z = ZoneId.of( "Africa/Tunis" ) ;
ZonedDateTime zdt = ldt.atZone( z ) ; // Determining an actual moment.
zdt.toString(): 2018-01-23T12:34:56+01:00[Africa/Tunis]
To see the same moment in UTC, extract an Instant.
Instant instant = zdt.toInstant() ;
Math
Represent a span of time unattached to the timeline as a Duration object.
Duration d = Duration.ofHours( 4 ) ; // Four hours, as an object.
Add to your LocalDateTime, if not using time zones.
LocalDateTime ldtLater = ldt.plus( d ) ;
If using zoned values, add to your ZonedDateTime.
ZonedDateTime zdtLater = zdt.plus( d ) ;
Those classes also offer shortcut methods, if you wish.
ZonedDateTime zdtLater = zdt.plusHours( 4 ) ; // Alternative to using `Duration` object.
One benefit of using a Duration rather than the shortcut methods is having an object that can be named.
Duration halfShiftLater = Duration.ofHours( 4 ) ;
…
ZonedDateTime zdtLater = zdt.plus( halfShiftLater ) ;
About java.time
The java.time framework is built into Java 8 and later. These classes supplant the troublesome old legacy date-time classes such as java.util.Date, Calendar, & SimpleDateFormat.
The Joda-Time project, now in maintenance mode, advises migration to the java.time classes.
To learn more, see the Oracle Tutorial. And search Stack Overflow for many examples and explanations. Specification is JSR 310.
You may exchange java.time objects directly with your database. Use a JDBC driver compliant with JDBC 4.2 or later. No need for strings, no need for java.sql.* classes.
Where to obtain the java.time classes?
Java SE 8, Java SE 9, and later
Built-in.
Part of the standard Java API with a bundled implementation.
Java 9 adds some minor features and fixes.
Java SE 6 and Java SE 7
Much of the java.time functionality is back-ported to Java 6 & 7 in ThreeTen-Backport.
Android
Later versions of Android bundle implementations of the java.time classes.
For earlier Android (<26), the ThreeTenABP project adapts ThreeTen-Backport (mentioned above). See How to use ThreeTenABP….
The ThreeTen-Extra project extends java.time with additional classes. This project is a proving ground for possible future additions to java.time. You may find some useful classes here such as Interval, YearWeek, YearQuarter, and more.
you can do something like
Calendar c = Calendar.getInstance();
c.setTimeInMillis(d2.getTime());
c.add(Calendar.HOUR_OF_DAY, 4);
d2 = c.getTime();
I recommend you using JDK8 time API or joda-time if you can.
Old java api for date is so bad!
In your case, you can:
//commons-lang3
Date oldDate = new Date();
Date newDate = DateUtils.addHours(oldDate, 1);
OR
convert date to timestamp, add some mills and convert timestamp back to date
I have a date string in Utc format -
String dateStr = "2017-03-03T13:14:28.666Z";
And I want to convert it to below format in Java date representation in ZonedDateTime.
When ZonedDateTime is printed it should show
String dateStr = "2017-03-03T00:00:00.000Z";
I have tried following code -
String timeZone = "America/Los_Angeles";
DateTimeFormatter dtf1 = DateTimeFormatter.ofPattern("yyyy-MM-dd'T'HH:mm:ss.SSSX");
DateTimeFormatter dtf2 = DateTimeFormatter.ofPattern("yyyy-MM-dd");
ZoneId zoneId1 = ZoneId.of(timeZone);
String dateStr = "2017-03-03T13:14:28.666Z";
Instant inst = Instant.parse(dateStr, dtf2);
ZonedDateTime dateTimeInTz = ZonedDateTime.ofInstant(inst, zoneId1);
ZonedDateTime startTime = dateTimeInTz.with(LocalTime.of(0, 0, 0, 0));
ZonedDateTime endTime = dateTimeInTz.with(LocalTime.MAX);
System.out.println("Start:"+startTime+", End:"+endTime);
System.out.println("Start:"+startTime.toString()+", End:"+endTime.toString());
ZonedDateTime nT = ZonedDateTime.of ( LocalDate.parse(dateStr, dtf1) , LocalTime.of (0,0,0,0) , ZoneId.of ( timeZone ) );
System.out.println("Start:"+nT);
Output:
Start:2017-03-03T00:00-08:00[America/Los_Angeles], End:2017-03-03T23:59:59.999999999-08:00[America/Los_Angeles]
Start:2017-03-03T00:00-08:00[America/Los_Angeles], End:2017-03-03T23:59:59.999999999-08:00[America/Los_Angeles]
Start:2017-03-03T00:00-08:00[America/Los_Angeles]
I want the start time to be normalized in ZonedDateTime.
I want to achieve it using java libraries only not any third party library.
tl;dr
You are working too hard.
Instant.parse( "2017-03-03T13:14:28.666Z" )
.truncatedTo( ChronoUnit.DAYS )
.toString()
2017-03-03T00:00.00Z
Details
What does "normalized in ZonedDateTime" mean? Please edit your Question to clarify.
When ZonedDateTime is printed it should show … "2017-03-03T00:00:00.000Z"
What you are asking is a contradiction. A ZonedDateTime has an assigned time zone for when you want to view a moment though the wall-clock time of a particular region. So asking for a ZonedDateTime to generate a string in UTC such as "2017-03-03T00:00:00.000Z" makes no sense. The Z is short for Zulu and means UTC.
Your input string is in standard ISO 8601 format. The java.time classes use these standard formats by default. So no need to specify a formatting pattern, no need for the DateTimeFormatter class.
Parse as an Instant, a point on the timeline in UTC with a resolution of nanoseconds.
Instant instant = Instant.parse( "2017-03-03T13:14:28.666Z" );
If you want midnight in UTC, truncate.
Instant instantMidnightUtc = instant.truncatedTo( ChronoUnit.DAYS );
instantMidnightUtc.toString(): 2017-03-03T00:00.00Z
No need for the ZonedDateTime class.
If you want to work with a date-only without any time-of-day and without a time zone, use the LocalDate class.
By the way, do not assume the first moment of the day is always 00:00:00. That is true for UTC. But various time zones may have anomalies such as Daylight Saving Time (DST) where the day may start at another time-of-day such as 01:00:00.
About java.time
The java.time framework is built into Java 8 and later. These classes supplant the troublesome old legacy date-time classes such as java.util.Date, Calendar, & SimpleDateFormat.
The Joda-Time project, now in maintenance mode, advises migration to the java.time classes.
To learn more, see the Oracle Tutorial. And search Stack Overflow for many examples and explanations. Specification is JSR 310.
Where to obtain the java.time classes?
Java SE 8 and SE 9 and later
Built-in.
Part of the standard Java API with a bundled implementation.
Java 9 adds some minor features and fixes.
Java SE 6 and SE 7
Much of the java.time functionality is back-ported to Java 6 & 7 in ThreeTen-Backport.
Android
The ThreeTenABP project adapts ThreeTen-Backport (mentioned above) for Android specifically.
See How to use ThreeTenABP….
The ThreeTen-Extra project extends java.time with additional classes. This project is a proving ground for possible future additions to java.time. You may find some useful classes here such as Interval, YearWeek, YearQuarter, and more.
String timeZone = "America/Los_Angeles";
DateTimeFormatter dtf1 = DateTimeFormatter.ofPattern("yyyy-MM-dd'T'HH:mm:ss.SSSX");
DateTimeFormatter dtf2 = DateTimeFormatter.ofPattern("yyyy-MM-dd");
ZoneId zoneId1 = ZoneId.of(timeZone);
String dateStr = "2017-03-03T13:14:28.666Z";
Instant inst = Instant.parse(dateStr, dtf2);
ZonedDateTime dateTimeInTz = ZonedDateTime.ofInstant(inst, zoneId1);
ZonedDateTime startTime = dateTimeInTz.with(LocalTime.of(0, 0, 0, 0));
ZonedDateTime endTime = dateTimeInTz.with(LocalTime.MAX);
String strStart = (startTime.toString().split("T"))[0] + "T00:00:00.000Z";
String strEnd = (endTime.toString().split("T"))[0] + "T00:00:00.000Z";
System.out.println("Start:"+strStart +", End:"+strEnd );
EDIT new method :
TimeZone timeZone = TimeZone.getTimeZone("Europe/Copenhagen");
Calendar cal = Calendar.getInstance(timeZone);
Calendar defaut = new GregorianCalendar( cal.get(Calendar.YEAR), cal.get(Calendar.MONTH), cal.get(Calendar.DAY_OF_MONTH),0,0,0);
You juste need to get all your necessary fields. With, for example, a dateFormat.
Hope it will help you
You can simply do:
DateUtils.truncate(yourDate, Calendar.DAY_OF_MONTH);
Hope this will help you
I have a string "2016-07-21T21:30:47.492+0000" I want to save it in DB in a column that has the datatype 'TIMESTAMP WITH TIMEZONE'. Kindly suggest the solution.
This is what I did:
final SimpleDateFormat mdyFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss.SSSSSX");
final SimpleDateFormat sdf = new SimpleDateFormat("dd-MM-yyyy");
final Date d1 = mdyFormat.parse(strDate);
final String mdx = sdf.format(d1);
You are using troublesome old classes now supplanted by java.time classes.
Here is how to follow the advice given by Jon Skeet posted in a comment on the Question.
java.time
The java.time framework is built into Java 8 and later. These classes supplant the old troublesome date-time classes such as java.util.Date, .Calendar, & java.text.SimpleDateFormat. The Joda-Time team also advises migration to java.time.
To learn more, see the Oracle Tutorial. And search Stack Overflow for many examples and explanations.
Much of the java.time functionality is back-ported to Java 6 & 7 in ThreeTen-Backport and further adapted to Android in ThreeTenABP.
OffsetDateTime
You can parse that input string as an OffsetDateTime object.
OffsetDateTime odt = OffsetDateTime.parse( "2016-07-21T21:30:47.492+0000" );
If your JDBC driver complies with JDBC 4.2 or later, you may be able to pass/fetch to SQL via the PreparedStatement::setObject and ResultSet::getObject methods. If not, convert to the old java.sql type.
Converting requires an Instant object. An Instant is a more basic building-block class in java.time, lacking the flexibility of an OffsetDateTime. The Instant class represents a moment on the timeline in UTC with a resolution up to nanoseconds. Extract an Instant from that OffsetDateTime.
Instant instant = odt.toInstant();
Pass the Instant to a new method added to the old java.sql class.
java.sql.Timestamp ts = java.sql.Timestamp.from( instant );
Then call the PreparedStatement::setTimestamp and ResultSet::getTimestamp methods.
myPreparedStatement.setTimestamp( 1 , ts );
…
java.sql.Timestamp ts = myResultSet.getTimestamp( 1 );
After fetching a java.sql.Timestamp, immediately convert to a java.time class, Instant. Use the java.sql classes only where direct support for java.time types is lacking in your JDBC driver, and even then, minimize your use of the java.sql classes. Do your business logic work in java.time.
Instant instant = ts.toInstant();
Confusing class names
Do not confuse the two old Date classes bundled with Java. The java.util.Date represents a date and a time-of-day. A java.sql.Date is intended to represent only a date-only value without a time-of-day (but confusing actually does have a time-of-day due to it being a clumsy hack of an awkward class design).
Avoid the java.util.Date and java.util.Calendar and java.text.SimpleDateFormat classes entirely. And minimize your use of the java.sql.Date/.Time/.Timestamp classes as discussed above.
Your code is having one problem
String strDate = "2016-07-21T21:30:47.492+0000";
final SimpleDateFormat mdyFormat = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss.SSSSSX");
// include `T` as well
final SimpleDateFormat sdf = new SimpleDateFormat("dd-MM-yyyy");
final Date d1;
try {
d1 = mdyFormat.parse(strDate);
// to add time zone you can use below line
// sdf.setTimeZone(TimeZone.getTimeZone("UTC"));
String mdx = sdf.format(d1);
System.out.println(mdx);
} catch (ParseException ex) {
}
Output without sdf.setTimeZone(TimeZone.getTimeZone("UTC"))
22-07-2016
Output with sdf.setTimeZone(TimeZone.getTimeZone("UTC"))
21-07-2016
TimeZone.getDefault() gets the system's default timezone.
I have a problem with parsing the following date from string: "1/29/2014 11:45:00 AM"
I do it the following way:
String source = "1/29/2014 11:45:00 AM";
Date startDate;
String sdfPattern = "MM/dd/yyyy hh:mm:ss aa";
SimpleDateFormat sdf = new SimpleDateFormat(sdfPattern, Locale.getDefault());
sdf.setTimeZone(TimeZone.getTimeZone("Europe/London"));
this.startDate = sdf.parse(source);
Interestingly, this works fine in a java project, but not in android. The error message I get:
01-15 15:36:46.950: W/System.err(2713): java.text.ParseException: Unparseable date: "1/29/2014 11:45:00 AM" (at offset 19)
Can anybody tell me what I am doing wrong?
Your format string specifies that you'll provide a two-digit month, but you're only providing "1".
I suspect you want:
String sdfPattern = "M/d/yyyy hh:mm:ss aa";
Additionally, the "AM/PM" designator is locale-sensitive (as are the date and time separators) . If you know that it will always use English, you should say so:
SimpleDateFormat sdf = new SimpleDateFormat(sdfPattern, Locale.US);
Unless the data is actually entered by the user (or being formatted for the user) you should avoid Locale.getDefault().
Your default locale may not match the AM/PM marker in the input String causing the exception. Try using
SimpleDateFormat sdf = new SimpleDateFormat(sdfPattern, Locale.ENGLISH);
java.time
The Question and other Answers use the troublesome old legacy date-time classes bundled with the earliest versions of Java. Now supplanted by the java.time classes.
ISO 8601
By the way, use the ISO 8601 formats when generating Strings to represent date-time values for exchange with other software. Your format is ambiguous and trickier to parse, unlike the standard formats.
DateTimeFormatter
The codes defining a formatting pattern in java.time.DateTimeFormatter are similar to the outmoded SimpleDateFormat but not exactly. So read the doc carefully.
String input = "1/29/2014 11:45:00 AM";
Locale locale = Locale.ENGLISH; // For translating the “AM” & “PM”.
DateTimeFormatter f = DateTimeFormatter.ofPattern ( "M/d/uuuu hh:mm:ss a" ).withLocale( locale );
LocalDateTime
Your input lacks any indication of an offset-from-UTC or a time zone. So we parse as a LocalDateTime object.
LocalDateTime ldt = LocalDateTime.parse ( input , f );
ldt.toString(): 2014-01-29T11:45
A LocalDateTime object purposely lacks any offset-from-UTC or time zone. That means it does not represent a moment on the timeline, only a rough idea about possible moments. You must assign an offset or time zone to give it meaning.
OffsetDateTime
If the context of your suggestions indicates this input was meant to be in UTC, apply the constant ZoneOffset.UTC to get an OffsetDateTime.
OffsetDateTime odt = ldt.atOffset ( ZoneOffset.UTC );
odt.toString(): 2014-01-29T11:45Z
ZonedDateTime
On the other hand, if the context indicates a specific time zone, apply a ZoneId to get a ZonedDateTime. The Questions seems to indicate that the Europe/London time zone is intended. Be aware that this time zone is not the same as UTC.
ZoneId z = ZoneId.of ( "Europe/London" );
ZonedDateTime zdt = ldt.atZone ( z );
zdt.toString(): 2014-01-29T11:45-05:00[America/Montreal]
About java.time
The java.time framework is built into Java 8 and later. These classes supplant the troublesome old date-time classes such as java.util.Date, .Calendar, & java.text.SimpleDateFormat.
The Joda-Time project, now in maintenance mode, advises migration to java.time.
To learn more, see the Oracle Tutorial. And search Stack Overflow for many examples and explanations.
Much of the java.time functionality is back-ported to Java 6 & 7 in ThreeTen-Backport and further adapted to Android in ThreeTenABP (see How to use…).
The ThreeTen-Extra project extends java.time with additional classes. This project is a proving ground for possible future additions to java.time. You may find some useful classes here such as Interval, YearWeek, YearQuarter, and more.
I am trying to parse an SQL date string (ISO 9075) and that uses microseconds(!) instead of milliseconds, for example
2010-11-22 08:08:08.123456
However, SimpleDateFormat refuses to recognize a pattern like "yyyy-MM-dd HH:mm:ss.SSSSSS" and "yyyy-MM-dd HH:mm:ss.SSS" does not work, either.
The code I am using looks something like this:
String dateString = "2010-11-22 08:08:08.123456";
String pattern = "yyyy-MM-dd HH:mm:ss.SSSSSS";
try
{
format = new SimpleDateFormat(pattern);
format.setLenient(false);
position.setIndex(0);
Date date1 = format.parse(dateString, position);
System.out.println("Date 1: " + date1);
Date date2 = format.parse(dateString);
System.out.println("Date 2: " + date1);
}
catch (Exception e) // Should not happen
{
e.printStackTrace();
}
Whichever of the 2 patterns (".SSS" or ".SSSSSS") I use, date1 is printer as null, whereas date2 causes a parsing exception (java.text.ParseException: Unparseable date).
Maybe chop the remaining fraction part out of the dateString before parse the date? I have the following
String dateString = "2010-11-22 08:08:08.123456";
String fraction = dateString.substring(dateString.length() - 3);
String formatString = dateString.substring(0, dateString.length() - 3);
String pattern = "yyyy-MM-dd HH:mm:ss.SSS";
ParsePosition position = new ParsePosition(0);
try
{
SimpleDateFormat format = new SimpleDateFormat(pattern);
format.setLenient(false);
position.setIndex(0);
Date date1 = format.parse(formatString, position);
System.out.println("Date 1: " + date1);
System.out.println("Date 1 fraction: " + fraction);
Date date2 = format.parse(formatString);
System.out.println("Date 2: " + date2);
System.out.println("Date 2 fraction: " + fraction);
}
catch (Exception e) // Should not happen
{
e.printStackTrace();
}
This allow the date to parse until millisecond precision while you still retain the fraction micro part.
Hmm. Given that Date doesn't have microsecond resolution, if you know that all the SQL date strings have the full six digits after the seconds decimal point (2010-11-22 08:08:08.000000 for example), why not just chop off the final three digits and use SimpleDateFormat on the remainder?
You may want to look at DATE4J which specifically tries to deal with database dates, to nanosecond precision.
You might want to call the DateFormat parse, because I think it will cut off the string. Try:
Date date1 = format.parse(dateString);
Plus, don't use "SSSSS". According to specs, only "SSS" is valid for dateformat.
Other than that, I agree with cutting it off or parsing in SQL.
Plus, you have setLenient to false, so it's strict. So the string, being longer is going to cause it to fail. Maybe that's why it returns null. Unsure, would have to test.
tl;dr
Insert/Update.
myPreparedStatement.setObject(
… ,
Instant.parse( "2010-11-22 08:08:08.123456".replace( " " , "T" ) + "Z" )
) ;
Retrieval.
LocalDateTime ldt = myResultSet.getObject( … , LocalDateTime.class ) ;
String output = ldt.toString().replace( "T" , " " ) ; // Remove the standard ISO 8601 format’s use of `T` in the middle with the SQL-style SPACE.
java.time
Java 8 brings the new java.time package, to supplant the notoriously troublesome old java.util.Date, .Calendar, and SimpleDateFormat classes. Those old legacy classes are limited to milliseconds resolution while your input string has microseconds. You cannot cram six decimal places into a data type limited to three.
The date-time values in java.time have nanosecond resolution, more than enough for your microseconds. That means up to nine decimal places for a fractional second.
With JDBC 4.2 and later, use the Instant class directly.
Parse your input String. To comply with ISO 8601 format used by default in the java.time classes, replace the SPACE in the middle with a T. Your given example must be coming from a column type TIMESTAMP WITHOUT TIME ZONE which means not a specific moment, not a point on the timeline.
String input = "2010-11-22 08:08:08.123456".replace( " " , "T" ) ;
LocalDateTime ldt = LocalDateTime.parse( input ) ;
And if this input was meant to be a moment in UTC, append a Z. Then you do have a moment, a specific point on the timeline. For use with a column type of TIMESTAMP WITH TIME ZONE.
String input = "2010-11-22 08:08:08.123456".replace( " " , "T" ) + "Z" ;
Instant instant = Instant.parse( input ) ;
Send to your database.
myPreparedStatement.setObject( … , instant ) ;
…and…
Instant instant = myResultSet.getObject( … , Instant.class ) ;
About java.time
The java.time framework is built into Java 8 and later. These classes supplant the troublesome old legacy date-time classes such as java.util.Date, Calendar, & SimpleDateFormat.
The Joda-Time project, now in maintenance mode, advises migration to the java.time classes.
To learn more, see the Oracle Tutorial. And search Stack Overflow for many examples and explanations. Specification is JSR 310.
You may exchange java.time objects directly with your database. Use a JDBC driver compliant with JDBC 4.2 or later. No need for strings, no need for java.sql.* classes.
Where to obtain the java.time classes?
Java SE 8, Java SE 9, and later
Built-in.
Part of the standard Java API with a bundled implementation.
Java 9 adds some minor features and fixes.
Java SE 6 and Java SE 7
Much of the java.time functionality is back-ported to Java 6 & 7 in ThreeTen-Backport.
Android
Later versions of Android bundle implementations of the java.time classes.
For earlier Android, the ThreeTenABP project adapts ThreeTen-Backport (mentioned above). See How to use ThreeTenABP….
The ThreeTen-Extra project extends java.time with additional classes. This project is a proving ground for possible future additions to java.time. You may find some useful classes here such as Interval, YearWeek, YearQuarter, and more.
UPDATE: The Joda-Time project is now in maintenance mode, with the team advising migration to the java.time classes. Leaving this section intact as history.
Joda-Time
As noted above, you should avoid using the java.util.Date, .Calendar, and SimpleDateFormat classes. As of Java 8 you have the choice of using java.time or Joda-Time or both, as they each their strengths and weaknesses. Joda-Time also works in earlier versions of Java.
You can parse that string using Joda-Time.
Alternatively, if you have access to the java.sql.Timestamp that generated your string, you can simply pass the Timestamp object to the constructor of a DateTime. I suggest also passing a time zone as DateTime objects know their own assigned time zone.
DateTime dateTime = new DateTime( mySqlTimestamp, DateTimeZone.UTC );
or
DateTime dateTime = new DateTime( mySqlTimestamp, DateTimeZone.forID( "Europe/Paris" ) );
Joda-Time has a resolution of milliseconds. So either way you generate the DateTime (parsing or passing), you will loose the finer fraction of the second (ignored/truncated, not rounded).
If you have control over the SQL date which is an input to the java code, you could try and retrieve the date from SQL in a format which will work ("yyyy-MM-dd HH:mm:ss.SSS").