更新:在 Postgres 9.4 中使用 to_regclass() 简单地测试存在性变得更加简单:
SELECT to_regclass('schema_name.table_name');
但请阅读详细信息:
功能齐全
您需要检查与名称冲突的任何类似表的对象,而不仅仅是序列。
如果名称可用,此函数会创建一个新序列,并在其他情况下分别发出有意义的NOTICE / WARNING / EXCEPTION:
CREATE OR REPLACE FUNCTION f_create_seq(_seq text, _schema text = NULL)
RETURNS void AS
$func$
DECLARE
_fullname text := format('%I.%I', COALESCE(_schema,current_schema),_seq);
_relkind "char" := (SELECT c.relkind
FROM pg_namespace n
JOIN pg_class c ON c.relnamespace = n.oid
WHERE n.nspname = COALESCE(_schema, current_schema)
AND c.relname = _seq);
BEGIN
IF _relkind IS NULL THEN -- name is free
EXECUTE 'CREATE SEQUENCE ' || _fullname;
RAISE NOTICE 'New sequence % created.', _fullname;
ELSIF _relkind = 'S' THEN -- 'S' = sequence
IF has_sequence_privilege(_fullname, 'USAGE') THEN
RAISE WARNING 'Sequence % already exists.', _fullname;
ELSE
RAISE EXCEPTION
'Sequence % already exists but you have no USAGE privilege.'
, _fullname;
END IF;
ELSE
RAISE EXCEPTION 'A(n) "%" named % already exists.'
-- Table-like objects in pg 9.4:
-- www.postgresql.org/docs/current/static/catalog-pg-class.html
, CASE _relkind WHEN 'r' THEN 'ordinary table'
WHEN 'i' THEN 'index'
-- WHEN 'S' THEN 'sequence' -- impossible here
WHEN 'v' THEN 'view'
WHEN 'm' THEN 'materialized view'
WHEN 'c' THEN 'composite type'
WHEN 't' THEN 'TOAST table'
WHEN 'f' THEN 'foreign table'
ELSE 'unknown object' END
, _fullname;
END IF;
END
$func$ LANGUAGE plpgsql;
COMMENT ON FUNCTION f_create_seq(text, text) IS
'Create sequence if name is free.
RAISE NOTICE on successful creation.
RAISE WARNING if it already exists.
RAISE EXCEPTION if it already exists and current user lacks USAGE privilege.
RAISE EXCEPTION if object of a different kind occupies the name.
$1 _seq .. sequence name
$2 _schema .. schema name (optional; default is CURRENT_SCHEMA)';
呼叫:
SELECT f_create_seq('myseq', 'myschema');
或者:
SELECT f_create_seq('myseq1'); -- defaults to current schema
解释
还要阅读代码末尾的函数注释。
-
在 Postgres 9.1+ 中工作。对于旧版本,您只需要替换format() - 即可防御 SQL 注入。详情:
两个单独的参数允许任何模式中的序列独立于当前search_path,还允许quote_ident() 完成其工作。 quote_ident() 使用模式限定名称失败 - 会模棱两可。
-
schema 参数有一个默认值,因此您可以在调用中省略它。如果没有给出模式,则函数默认为current_schema。 Per documentation:
current_schema 返回位于
搜索路径(如果搜索路径为空,则为空值)。这是
将用于任何表或其他命名对象的模式
是在没有指定目标架构的情况下创建的。
pgclass.relkind in the manual 的类型列表。
PostgreSQL error codes.