Earliest Timestamp supported in PostgreSQL

前端 未结 2 1387
时光取名叫无心
时光取名叫无心 2021-02-18 18:43

I work with different databases in a number of different time zones (and periods of time) and one thing that normally originates problems, is the date/time definition.

F

相关标签:
2条回答
  • 2021-02-18 19:34

    The manual states the values as:

    • Low value: 4713 BC
    • High value: 294276 AD

    with the caveat, as Chris noted, that -infinity is also supported.

    See the note later in the same page in the manual; the above is only true if you are using integer timestamps, which are the default in all vaguely recent versions of PostgreSQL. If in doubt:

    SHOW integer_datetimes;
    

    will tell you. If you're using floating point datetimes instead, you get greater range and less (non-linear) precision. Any attempt to work out the minimum programatically must cope with that restriction.

    PostgreSQL does not just let you cast zero to a timestamp to get the minimum possible timestamp, nor would this make much sense if you were using floating point datetimes. You can use the julian date conversion function, but this gives you the epoch not the minimum time:

    postgres=> select to_timestamp(0);
          to_timestamp      
    ------------------------
     1970-01-01 08:00:00+08
    (1 row)
    

    because it accepts negative values. You'd think that giving it negative maxint would work, but the results are surprising to the point where I wonder if we've got a wrap-around bug lurking here:

    postgres=> select to_timestamp(-922337203685477);
              to_timestamp           
    ---------------------------------
     294247-01-10 12:00:54.775808+08
    (1 row)
    
    postgres=> select to_timestamp(-92233720368547);
              to_timestamp           
    ---------------------------------
     294247-01-10 12:00:54.775808+08
    (1 row)
    
    postgres=> select to_timestamp(-9223372036854);
             to_timestamp         
    ------------------------------
     294247-01-10 12:00:55.552+08
    (1 row)
    
    postgres=> select to_timestamp(-922337203685);
    ERROR:  timestamp out of range
    postgres=> select to_timestamp(-92233720368);
              to_timestamp           
    ---------------------------------
     0954-03-26 09:50:36+07:43:24 BC
    (1 row)
    
    postgres=> select to_timestamp(-9223372036);
             to_timestamp         
    ------------------------------
     1677-09-21 07:56:08+07:43:24
    (1 row)
    

    (Perhaps related to the fact that to_timestamp takes a double, even though timestamps are stored as integers these days?).

    I think it's possibly wisest to just let the timestamp range be any timestamp you don't get an error on. After all, the range of valid timestamps is not continuous:

    postgres=> SELECT TIMESTAMP '2000-02-29';
          timestamp      
    ---------------------
     2000-02-29 00:00:00
    (1 row)
    
    postgres=> SELECT TIMESTAMP '2001-02-29';
    ERROR:  date/time field value out of range: "2001-02-29"
    LINE 1: SELECT TIMESTAMP '2001-02-29';
    

    so you can't assume that just because a value is between two valid timestamps, it is its self valid.

    0 讨论(0)
  • 2021-02-18 19:48

    The earliest timestamp is '-infinity'. This is a special value. The other side is 'infinity' which is later than any specific timestamp.

    I don't know of a way of getting this programaticly. I would just use the value hard-coded the way you might use NULL. That means you have to handle infinities on the client side though.

    0 讨论(0)
提交回复
热议问题