Handling time zones in Go
Many beginner developers get confused in dealing with timezones. This article explains -
- How to store them in DB?
- How to parse them in Go?
When timezone is stored in the DB, always stick to one standard timezone, the ideal would be to save UTC time and while presenting them, convert it to various timezones as per requirement.
I am taking MySQL as an example of storing time, but the below solution is DB agnostic. As per MySQL documentation, There are two ways one can store time in MySQL.
- DATETIME — The DATETIME type is used for values that contain both date and time parts. MySQL retrieves and displays DATETIME values in
YYYY-MM-DD hh:mm:ss
format. The supported range is1000-01-01 00:00:00
to9999-12-31 23:59:59
. - TIMESTAMP — The TIMESTAMP datatype is used for values that contain both date and time parts. TIMESTAMP has a range of
1970-01-01 00:00:01
UTC to2038-01-19 03:14:07
UTC.
In this article, I will use DATETIME for example.
Now, the other and most important thing is to read and convert it into any timezone.
Below is an example of how we can achieve this in Go. Let’s first define a map from country to IANA identifiers and some utility functions. s
You can play with the full example in the Go playground
Caveat:
As per go documentation of Load location, The time zone database needed by LoadLocation may not be present on all systems, especially non-Unix systems. LoadLocation looks in the directory or uncompressed zip file named by the ZONEINFO
environment variable, if any, then looks in known installation locations on Unix systems, and finally looks in $GOROOT/lib/time/zoneinfo.zip
.
With Docker:
By default, it comes with Go installation. but in case you deploy using Docker and build multi-stage docker Alpine image. You can add line given below.
RUN apk add tzdata
This will add timezone information into /usr/share/timezone in the alpine image.
Also, do not forget to set the Environment variable ZONEINFO to /usr/share/timezone.
ZONEINFO=/usr/share/timezone
Just for reference, Below is the sample Dockerfile.