So, I’ve been working on a new multi-tier cloud project for a while, and ran into a major issue regarding date/times, specific to a time-sensitive date/time that must be configurable in different timezones, for a specific timezone. Of course, this is a very specific scenario, but the fact is, managing date/times on the client side can be a real pain in the… knees? I mean truly, if you can’t walk that sucks, almost as bad as not being able to sit.

One big thing to note here… this is not a matter of converting UTC time to local time, that is actually very easy to do.

Anyways, There’s a lot to deal with when you are working with the Date object in Javascript, not only are dates returned arbitrarily from JSon as a crazily formatted digit, but next, browsers start to mess with the display of dates. There’s also a lot of questions that can come up during this timeframe…

  • How should I store the dates?
  • How do I convert the dates?
  • Do I convert the dates back before reaching the client?
  • If I do convert dates back, and the browser changes it further, then I have to write a library to change it back….
  • Do I need to make the dates into a string and parse it manually?
  • What do I want for lunch?
  • What is the real meaning of life?

I went through a painstaking process of first determining where the date/time changes were coming from (SQL=> WCF),(WCF=>WebClient),(WebClient=>Json), (Json=>localclient)… and it turns out, this happens when the date/time is being rendered to the client. I won’t go into all the different tests/steps and frameworks I tried to use for fixing the issue, but I will go into how I fixed the issue and how to deploy such a solution in MVC.

First, you have get timezone data that you would like to use, and create a action method (more on this later) for returning this data… this timezone data is available for free here: http://www.iana.org/time-zones, you will want to select “Time Zone Data” not “Time Zone Code”… this will contain timezone data for areas in the world.

Next you want to pick up two different JavaScript libraries, TimezoneJS and jsTimezoneDetect which will help determine and convert the local timezone into the timezone of your target (mine specifically is PST).

public ActionResult GetTz(string id)
        {
            string file = Server.MapPath("~/Content/tz/" + id);
            if (System.IO.File.Exists(file))
                return File(file, "application/java-archive");
            else
                return RedirectToAction("Index2");

        }

Now, as far as DT storage on the server side… for cloud/major internet apps, UTC is the way to go, but if you have a specific timezone you need to target, this will create issues when creating, updating and displaying these dates through javascript/json async post-backs. So in my case, the user is entering dates in a PST format (the start and end time of a specific item), which is then saved in a UTC format using .NET:

TimeZoneInfo.ConvertTimeToUtc(newItem.StartDate, TimeZoneInfo.FindSystemTimeZoneById("Pacific Standard Time"))

Now that the DT is stored in a UTC format, you can return the DT to the client unchanged, in UTC format and the libraries will do the rest…. kind-of… there’s still some configuration needed if you are deploying a solution similar to mine, where I’m loading the data on pageload, that needs the DT’s formatted. First we determine which timezone the person loading the browser is, and saving this into a variable to be used later:

var timezone = jstz.determine();

Next, we write an MVC method that allows us to utilize the library(s) you downloaded earlier for timezone data, and returns this data to the client.

 

Note, I placed the files that were returned from the library into a /tz folder in the Content directory, and set all files that would need to be transferred on publish, Build Action = “Content”, so when you deploy the MVC project, it will deploy these files as well.

Now that we have our files, and a method to retrieve them, we can move ahead and get our timezones… We need to set our zoneFileBasePath:

timezoneJS.timezone.zoneFileBasePath = '/YourController/GetTz';

Setting async here is important if you are loading data that requires the formatting initially. within the brackets we write all our JS to work with the timezone data… to get the date from a json return properly, we will now create a new date using the timezoneJS library, set it to the current timezone name, and then change the timezone. This converts from UTC to local, and then local to another timezone:

var dt = new timezoneJS.Date(parseInt(jsonDate.substr(6), timezone.name()));
dt.setTimezone('America/Los_Angeles');

 

The idea is to make sure that all admins who configure something (that needs to be PST), no matter where they login, they will see accurate PST DT’s.

There’s a lot more to these libraries than I’ve included above, but wanted to share the joy that is, having DT’s to serve up specific timezone data globally through the cloud.

*DT = DateTime

Advertisements