The MySQL TIMESTAMP
data type is perfect for this problem. They are always stored in UTC
(as long as your server's OS isn't set up bizarrely time-zone-wise). As long as the OS's clock is in UTC, you'll be in good shape.
Then when you give MySQL commands like these:
SET time_zone = 'America/New_York';
INSERT INTO notification (deliver_timestamp, '2020-11-20 11:30:00')
On the way in to store a TIMESTAMP
MySQL converts it from the current time to UTC. And on the way out it converts it back to local time. So, if you do this, for example.
SET time_zone = 'America/Los_Angeles';
SELECT timestamp FROM notifications;
you'll get 1010-11-20 08:30:00
which is the same time, but three hours behind. The strings like America/New_York
and Asia/Kolkata
are the names of the time zones. MySQL and other software that uses this sort of zoneinfo timezone name knows all the electropolitical stuff about when various places switch from daylight to regular. Not to mention historical changes to those rules going back more than half a century. It's a sophisticated system.
To get this to work
To get this to work globally you must have a Timezone user-preference setting for each person who uses your system. You'll have to rig up some sort of dropdown menu that shows the timezone names from the zoneinfo data base. You need that zoneinfo name for MySQL's SET time_zone='zoneinfoname'
command. You can use these same text strings with the java.time.ZonedDateTime class.
Then, each time you access your database on behalf of a user, you set the time zone before you do anything else. In a typical web app each user's timezone preference is part of their user profile.
Notice: only TIMESTAMP
columns work this way. DATETIME
columns store and retrieve whatever time data you give them, without any notice of time zones.
And, if your Java code needs UTC time, do this.
SET time_zone = 'UTC';
SELECT timestamp FROM notifications;
It can be a little hard to wrap your head around this. MySQL uses the zoneinfo rules for these conversions. Zoneinfo knowswhen the time is DST and when it is not.