Consider removing `local_datetime`
See original GitHub issueIdea
Make a single datatype for a timestamp which is basically UTC datetime.
Motivation
- There are very little use cases (if any) of the type
- It’s a source of lots of errors
- If you really want it, think twice and use two fields for date and time (i.e. date when alarm first started and time when it should ring for a recurring alarm, instead of cobining the two)
What other databases are doing?
Terms:
- naive – timestamp without timezone specified (for example
2019-11-25 22:10:42
if written as string) - unix timestamp – specific representation of datetime in seconds since the unix epoch (epoch is in UTC so the whole value doesn’t depend on the time zone)
- UTC-normalized timestamp – means datetime stored as UTC internally being it unix timestamp or timestamp at UTC
Databases:
- PostgreSQL has
TIMESTAMP
which is documented to be UTC but accepts a naive timestamp as an input, so easy to misuse. AndTIMESTAMPTZ
which accepts any timezone offset as input and converts to UTC timestamp internally. Converts to client session time on output. - MySQL has
TIMESTAMP
which accepts a naive timestamp in local time and does autoconversion to UTC for storage.DATETIME
is just a naive timestamp without conversion - VoltDB uses UTC-normalized
TIMESTAMP
. As long as I understand it has Java API and it’s hard to mess with timezones (because it’s converted from java.date.Date that is basically a unix timestamp) - MongoDB has UTC-normalized timestamp named
Date
(as far as I understand when converting to/from a string they only acceptZ
-suffixed format2019-11-25T22:10:42Z
). Name probably inherits JavaScript type name - Clickhouse use naive format that is converted to/from local time, named
DateTime
(basically likeTIMESTAMP
in mysql) - FoundationDB (in document layer) basically supports MongoDB semantics
- RethinkDB actually store timestamp + timezone, named
time
- Cassandra uses UTC-normalized
timestamp
and auto-converts to timezone in some clients - Redis has no datatype for storing datetimes but uses unix timestamp (in seconds) in commands like
EXPIREAT
Conclusions:
- Except in PostgreSQL and MySQL every database has a single datetime type (most of them don’t have separate date or time, though)
- Whereas PostgreSQL and MySQL looks like were trying to fix a mistake, that’s why they added a type, not because two types needed
- Timestamp means different things in different databases so it’s okay to give it our own meaning (i.e. rename datetime -> timestamp)
Update: added cassandra
Issue Analytics
- State:
- Created 4 years ago
- Reactions:1
- Comments:14 (14 by maintainers)
Top Results From Across the Web
LocalDateTime remove the milliseconds - java - Stack Overflow
I am working on java application where i am using Java 8. I have integrated the database(multiple database Oracle, Mysql, Postgres) and where...
Read more >Convert LocalDateTime to LocalDate, remove the time part
Question. We would like to know how to convert LocalDateTime to LocalDate, remove the time part. Answer. import java.time.
Read more >LocalDateTime (Java Platform SE 8 ) - Oracle Help Center
Returns a copy of this LocalDateTime with the time truncated. Truncation returns a copy of the original date-time with fields smaller than the...
Read more >jdk8u-jdk/LocalDateTime.java at master - GitHub
* This method only considers the position of the two date-times on the local time-line. * It does not take into account the...
Read more >LocalDate minusDays() method in Java with Examples
The minusDays() method of LocalDate class in Java is used to subtract the number of specified day from this LocalDate and return a...
Read more >Top Related Medium Post
No results found
Top Related StackOverflow Question
No results found
Troubleshoot Live Code
Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start FreeTop Related Reddit Thread
No results found
Top Related Hackernoon Post
No results found
Top Related Tweet
No results found
Top Related Dev.to Post
No results found
Top Related Hashnode Post
No results found
Top GitHub Comments
Alright, I’ve given this some thought in light of the discussion of this topic on our team call today. Here’s the TL;DR part:
local_datetime
datatype.local_datetime
,local_time
, andlocal_date
toclock_datetime
,clock_time
, andclock_date
.At this point I think we should wind down this discussion and focus on shipping Alpha 2.
Paul’s main motivation to remove the
local_datetime
type falls down to:Regarding (1): I believe this should be addressed by providing a better documentation and appropriate naming. I admit that the current “local” term can be confusing. Since in all of our discussions we always say that “local time” is about “clock time” I think we should just rename our naive types to use the word “clock”.
Regarding (2): First, I don’t think that the use case is marginal. We did use a “reminders” app as an example for when some developers would prefer to use
local_datetime
. But it goes deeper than that; notifications, schedules, do not disturb times, alarms: they all conceptually operate in local time to the user. I can totally see our own cloud offering having user settings for when we should send our users performance reports or analytics. Such settings are location independent, i.e. it does not matter where the user is, did a DST transition happen or not—a user just wants to see their report on Wednesday at 10am local time.Paul argues that for a marginal use case like that a tuple of
(local_date, local_time)
can be used. True, but then there is no way our users can perform date/time arithmetic on such values. How would a user shift all their local date/time values 10 minutes to the future? Or how do you express “send me a message 10 minutes prior to [this local date/time]”? How would you implement school schedule app without using local date/time? Saying all these examples are “not realistic” or “not relevant” does not cut it, sorry. And here we arrive to another topic: how do we want to design EdgeDB. What features should make it and what should not?In my opinion, it’s finding the balance between understanding if a feature addresses a marginal or a popular use case, and between whether it is possible to emulate the feature if a user is facing that marginal use case. And for
local_datetime
the answer is simple: implementing date/time arithmetic for a(local_date, local_time)
tuple would move our users to the world of pain. They wouldn’t be able to usestd::duration
; they would either have to implement their custom date/time arithmetic via EdgeQL functions or to fetch the data and perform the calculation on the client side. But what if a user wants to update millions of values? All of them? This quickly becomes impractical.If we want to be fanatical about this we can also drop
std::local_date
andstd::local_time
—they can also be easily implemented with a simple named tuple. And probably we don’t wantstd::duration
at that point. Would that be convenient? Well, for some users it wouldn’t matter, but some would just continue using PostgreSQL because it offers all these features and EdgeDB would be just inferior to it.We want EdgeDB and EdgeQL to be feature rich so that people solve less of data-related mundane problems on the client side. So let’s continue doing that.
Further, I don’t believe that maintaining
std::local_datetime
would require any significant effort.Regarding (3): this is a rather weak point as many databases nowadays are treated as dumb data stores. Little effort, if any, goes into designing good standard libraries, data types, and query languages. Naturally our philosophy is quite different from theirs and this is what separates EdgeDB from the competition.
Regarding (4): this doesn’t really matter in this context. When you are dealing with a programming language it is easy to just install a third-party library for any missing functionality. Databases are different—it’s not easy to install an extension in your hosted DB. Building useful date/time arithmetic abstractions for
(local_date, local_time)
tuples would be problematic even in EdgeQL.That said I’m grateful to Paul for highlighting the fact that our current naming is non-obvious. “local” can be ambiguous to users, and “naive” or “clock” prefix would read way better.
I think we should rename
std::local_
types tostd::naive_
orstd::clock_
. Either name would work fine IMO.I’m -1 on renaming
std::datetime
tostd::timestamp
. The key problem is that thetimestamp
type in Postgres is a direct opposite to ourstd::datetime
. Given that EdgeDB is based on Postgres I can imagine that a lot of users would be confused and would be looking for thestd::timestamptz
type spending time and asking questions on StackOverflow.I’m -1 on renaming
std::local_datetime
tostd::date
. JavaScript and Swift useDate
for full date/time types, so I think thatstd:date
would be confusing.Decided to move it into a namespace #902