投射到自定义域PostgreSQL

时间:2018-06-21 10:44:11

标签: sql postgresql types casting

我正在尝试创建一个自定义域类型来强制多个表的约束。
约束可以很好地工作,但是我还想添加自定义类型转换,该类型将在实际类型转换和检查之前应用小写字母。

CREATE DOMAIN email AS varchar(80)
  CHECK (value ~ ('^[a-z0-9!#$%&''*+/=?^_`{|}~-]+(?:\.[a-z0-9!#$%&''*+/=?^_`{|}~-]+)*@' ||
                  '(?:[a-z0-9](?:[a-z0-9-]*[a-z0-9])?\.)+[a-z0-9](?:[a-z0-9-]*[a-z0-9])?$'));

CREATE OR REPLACE FUNCTION text_as_email(text)
  RETURNS email
LANGUAGE SQL AS
$$ SELECT lower($1) :: email $$;

CREATE CAST ( text AS email )
WITH FUNCTION text_as_email(text) AS IMPLICIT;

域和功能均按预期工作

SELECT 'abc@abc.com' :: email; -- no errors
SELECT 'abc@@abc.com' :: email; -- expected error
SELECT text_as_email('ABC@abc.com'); -- no errors, returns 'abc@abc.com'

但是强制转换无法转换大写

SELECT 'ABC@abc.com' :: email; -- gives an error

任何想法,我都会感激的。

1 个答案:

答案 0 :(得分:2)

来自the documentation:

  

强制转换为域类型或从域类型强制转换当前无效。向域或从域进行强制转换使用与其基础类型关联的强制转换。

创建演员表时会警告您:

CREATE CAST ( text AS email )
WITH FUNCTION text_as_email(text) AS IMPLICIT;

WARNING:  cast will be ignored because the target data type is a domain