我想阻止任何沒有時區的時間戳被插入到PostgreSQL SQL
函數中。唯一的辦法我設法拿出不起作用,因爲Postgres的似乎只是忽略任何時區的字符串後綴,而是使用了時區從服務器:PostgreSQL:如何測試時間戳是否有時區?
hostname:~ username$ date
Tue Sep 27 15:30:16 CEST 2016
hostname:~ username$ uname -a
Darwin hostname.domain 14.5.0 Darwin Kernel Version 14.5.0: Mon Aug 29 21:14:16 PDT 2016; root:xnu-2782.50.6~1/RELEASE_X86_64 x86_64
hostname:~ username$ psql -U postgres
psql (9.5.3)
Type "help" for help.
postgres=# SELECT extract(TIMEZONE FROM '2016-09-19 01:00:00'::timestamptz);
date_part
-----------
7200
(1 row)
postgres=# SELECT extract(TIMEZONE FROM '2016-09-19 01:00:00+0200'::timestamptz);
date_part
-----------
7200
(1 row)
postgres=# SELECT extract(TIMEZONE FROM '2016-09-19 01:00:00+0800'::timestamptz);
date_part
-----------
7200
(1 row)
我有一種感覺,我通常誤解的東西。誰能幫忙?
更新20160928:
爲了給一些解釋性背景下,這是我的數據庫(精簡到什麼是眼下的問題必不可少):
CREATE DATABASE my_db;
CREATE TABLE my_table
(
id serial PRIMARY KEY,
timestamp_utc timestamp with time zone NOT NULL,
title text NOT NULL
);
,這是我的函數以其當前形式插入數據:
CREATE FUNCTION insert_row
(
p_timestamp_utc timestamp with time zone,
p_title text
)
RETURNS integer
LANGUAGE SQL
SECURITY DEFINER
VOLATILE
AS
$BODY$
INSERT INTO my_table
( timestamp_utc title)
VALUES (p_timestamp_utc, p_title)
RETURNING id;
$BODY$;
我創建了一個SQLFiddle;創建有保留,雖然沒有功能...
問題:
調用函數成功,即使時間戳參數不攜帶一個時區:
SELECT insert_row('2016-09-01 01:00:00'::timestamptz, 'some title');
,我需要找到一種使這個函數調用失敗的方法。
原因爲什麼我需要做到這一點是因爲我想定義什麼時區是由代碼強制執行的;另一種選擇是數據庫服務器和客戶端在某種程度上隱含地/默默地同意一個約定 - 並且這聽起來不像是一個聰明的舉動......
感謝您的信息!:-)雖然你的回答肯定是內容豐富的,但它並沒有真正幫助我防止任何沒有時區的時間戳插入到我的數據庫中,是嗎? – ssc
我試圖解決你的「一般誤解」。爲了讓我能夠幫助你解決問題,你能解釋一下你插入PostgreSQL SQL函數*的含義嗎? –