1

Do you guys know how to eleminate the TimeZone part from servicestack.text JsonSerializer's result? It's currently like

2015-06-30T23:59:00.0000000+08:00

, I want it to be

2015-06-30T23:59:00.0000000

Thx a lot!

Matt Johnson-Pint
  • 230,703
  • 74
  • 448
  • 575
iNc0ming
  • 383
  • 1
  • 6
  • 17

3 Answers3

3

Service Stack is probably doing the right thing. Check the .Kind property of the DateTime you are serializing. If you don't want a time zone offset included, then it should be DateTimeKind.Unspecified. My guess is that your value has DateTimeKind.Local, so it is capturing your local offset.

Consider the following code:

JsConfig.DateHandler = JsonDateHandler.ISO8601;
Debug.WriteLine(JsonSerializer.SerializeToString(DateTime.Now));
Debug.WriteLine(JsonSerializer.SerializeToString(DateTime.UtcNow));
Debug.WriteLine(JsonSerializer.SerializeToString(new DateTime(2013, 1, 1)));

Output on my machine:

"2013-07-27T11:42:02.3711281-07:00"
"2013-07-27T18:42:02.4071518Z"
"2013-01-01T00:00:00.0000000"
Matt Johnson-Pint
  • 230,703
  • 74
  • 448
  • 575
  • but the DateTime is pulled out from the database by EntityFramework, there's no way to specify the .Kind. – iNc0ming Jul 27 '13 at 18:43
  • Ahhh.. now you have a different question. :) There is probably a way to do it in EF, but you could always change it yourself with `DateTime.SpecifyKind`. – Matt Johnson-Pint Jul 27 '13 at 18:44
  • I think EntityFramework or Service Stack just takes the server's timezone, which is in UTC. – iNc0ming Jul 27 '13 at 18:48
  • I'm pretty sure EF uses `Unspecified` as its default. I've found a few posts talking about how to set it explicitly to UTC, such as [this one](http://www.aaroncoleman.net/post/2011/06/16/Forcing-Entity-Framework-to-mark-DateTime-fields-at-UTC.aspx) and [this one](http://stackoverflow.com/q/1906331/634824) – Matt Johnson-Pint Jul 27 '13 at 18:51
  • [Here is a good article on this.](http://blog.3d-logic.com/2012/04/08/entity-framework-and-datetime-of-unspecified-kind/) – Matt Johnson-Pint Jul 27 '13 at 18:54
  • So if you are seeing `Local` kinds, then either you are setting them yourself, or somewhere you are using `DateTime.Now` to fill the property. – Matt Johnson-Pint Jul 27 '13 at 18:55
  • @MattJohnson, that is not correct, at least not what concerns deserialization of DateTime in UTC kind. I serialize utc datetime data and upon deserialization it magically converts back to local which is highly undesirable. Is that a bug? Or why does it convert without being asked to do so? – Matt Apr 28 '14 at 09:36
  • @MattWolf would you please post that as a new question an provide supporting details? Thanks. – Matt Johnson-Pint Apr 28 '14 at 15:54
  • 1
    @MattJohnson, my apologies I did not realize this is not directly related to the question at hand, I think with the newer versions `AlwaysUseUtc` and `AssumeUtc` take care of described problem. – Matt Apr 29 '14 at 00:58
3

Just to add my .02$ on this topic since I've spent quite some time during past several years playing with systems that span across different timezones.

Basically it boils down to NEVER use DateTime.Now; always go with DateTime.UtcNow. I've made a custom component that allowed me to have DateTimeCustom.Now that gave me Now in specific timezone (so no matter what is the timezone on the server I could always have "local" time); it worked in practice but eventually I ended up tying it to UTC (DateTimeCustom.Now = DateTime.UtcNow)... since the biggest problem was converting to different timezones from "your" timezone - you don't want to go there.

So basically:

  1. Everything you do on the server, go with DateTime.UtcNow. If you have some logs that are just for you and you only, and you REALLY want to keep it in whatever timezone is the server... sure, go for it. Just remember what I said when you go on a trip a half way across the globe and need to look at the logs.

  2. If client is sending in dates to the server (i.e. there is no way to do DateTime.UtcNow), convert what he sent to UTC and save that to db. Sure... "convert what client sents to UTC" is easier said than done, but answers like this once can help a lot.

  3. If you are displaying dates, use ServiceStack.Text for serializing Json and set JsConfig.DateHandler = DateHandler.ISO8601; & JsConfig.AssumeUtc = true;

  4. On the client use AngularJs and it'll handle displaying date/time in local timezone with ease, like {{myobj.mydate | date:'HH:mm:ss'}}

Community
  • 1
  • 1
nikib3ro
  • 20,366
  • 24
  • 120
  • 181
1

Ok, problem solved. It ends up in 2 lines code:

JsConfig<DateTime>.SerializeFn = dt => dt.ToString("s");
JsConfig<DateTime?>.SerializeFn = dt => dt.HasValue ? dt.Value.ToString("s") : "null";
Gian Marco
  • 22,140
  • 8
  • 55
  • 44
iNc0ming
  • 383
  • 1
  • 6
  • 17