最初创建参数表,并在Postgres中添加一行。
此表应始终为一行,否则使用此表的SQL查询将产生不正确的结果。不允许DELETE
或INSERT
到此表,仅允许UPDATE
。
如何在此表中添加单行约束?
也许DELETE
和INSERT
触发器可以引发异常或者是否有更简单的方法?
答案 0 :(得分:4)
以下将创建一个表,您只能插入一行。 id
列的任何更新都会导致错误,任何插入的值都不会超过42.实际的id
值实际上并不重要(除非有一些特殊含义,你需要)。
create table singleton
(
id integer not null primary key default 42,
parameter_1 text,
parameter_2 text,
constraint only_one_row check (id = 42)
);
insert into singleton values (default);
要防止删除,您可以使用规则:
create or replace rule ignore_delete
AS on delete to singleton
do instead nothing;
如果你想insert
"失败"你也可以使用规则让insert
什么都不做。默默。如果没有该规则,insert
将生成错误。如果您希望delete
也生成错误,则需要创建一个简单引发异常的触发器。
修改强>
如果要为插入或删除引发错误,则需要触发:
create table singleton
(
id integer not null primary key,
parameter_1 text,
parameter_2 text
);
insert into singleton (id) values (42);
create or replace function raise_error()
returns trigger
as
$body$
begin
RAISE EXCEPTION 'No changes allowed';
end;
$body$
language plpgsql;
create trigger singleton_trg
before insert or delete on singleton
for each statement execute procedure raise_error();
请注意,您必须在创建触发器之前插入单行,否则无法插入该行。
这仅对超级用户或表的所有者有效。两者都有权删除或禁用触发器。但这是超级用户的本质 - 他可以做任何事情。
答案 1 :(得分:1)
要使任何表格成为单身,只需添加此列:
just_me bool NOT NULL DEFAULT TRUE UNIQUE CHECK (just_me)
这只允许一行。另外添加触发器@a_horse provided。
但是为了这个目的,我会而不是使用函数而不是表。更简单,更便宜。
CREATE OR REPLACE FUNCTION one_row()
RETURNS TABLE (company_id int, company text) LANGUAGE sql IMMUTABLE AS
$$SELECT 123, 'The Company'$$
ALTER FUNCTION one_row() OWNER TO postgres;
将所有者设置为应该允许更改它的用户。
没有其他人改变它 - 当然除了超级用户。超级用户可以做任何事情。
您可以像使用表格一样使用此功能:
SELECT * FROM one_row();
如果您需要“表格”,请创建一个视图(实际上是内部的特殊表格):
CREATE VIEW one_row AS SELECT * FROM one_row();
答案 2 :(得分:0)
我猜你不会在你的应用程序中使用PostgreSQL root用户,所以你可以简单地限制你的应用程序用户对这个表的UPDATE
的权限。
INSERT
或DELETE
会导致Insufficient privilege
例外。