I have a datetime in database which I read using SqlDataReader and then cast it to (DateTime)
. After the cast its Kind
property is DateTimeKind.Unspecified
.
Then I have another string which I read from some other source. Its format is like this 2016-01-20T22:20:29.055Z
. I do DateTime.Parse("2016-01-20T22:20:29.055Z")
and its Kind property is DateTimeKind.Local.
How do I properly parse the both date times for comparison? Do I need to use DateTimeOffsets? How should I parse them?
Thanks
Parse converts the datetime string into a DateTime . It automatically tries to figure out the datetime format. The DateTime. ParseExact method converts the specified string representation of a datetime to a DateTime . The datetime string format must match the specified format exactly; otherwise an exception is thrown.
ParseExact(String, String, IFormatProvider) Converts the specified string representation of a date and time to its DateTime equivalent using the specified format and culture-specific format information. The format of the string representation must match the specified format exactly.
Using strptime() , date and time in string format can be converted to datetime type. The first parameter is the string and the second is the date time format specifier. One advantage of converting to date format is one can select the month or date or time individually.
Because SQLReader cannot reasonably infer a DateTimeKind, it leaves it as unspecified. You'll want to use DateTime.SpecifyKind
to change the DateTimeKind on your output from the SQLReader to the appropriate value. This works ok if you are only dealing with UTC and one consistent local time zone; otherwise, you really should be using DateTimeOffset in both your code and the SQL Database.
The string "2016-01-20T22:20:29.055Z" is ISO 8601 compliant and is a UTC date; however, DateTime.Parse
with only 1 argument can end up performing a conversion to local time. Per the documentation:
Generally, the Parse method returns a DateTime object whose Kind property is DateTimeKind.Unspecified. However, the Parse method may also perform time zone conversion and set the value of the Kind property differently, depending on the values of the s and styles parameters:
Also see UTC gotchas in .NET and SQL Server in Derek Fowler's blog for additional coverage on the topic.
In your second example, 2016-01-20T22:20:29.055Z
has timezone information provided with it; the 'Z' at the end indicates that the timestamp is intended for Coordinated Universal Time (UTC). However, DateTime.Parse()
will default its conversion using DateTimeKind.Local
unless a specific timezone is specified. You can use DateTime.ParseExact
to be more specific.
As to why the datetime values in your database are coming out as Unspecified
, that's likely because they contain no timezone indication at all. Check to see if your database values specify timezone information, either by using 'Z' at the end or specifying an exact timezone, such as 2016-01-20T22:20:29.055-07:00
(UTC-7).
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With