我的restrictionsPostgreSQL 数据库中有一个小(约 10 行)表,其中每天删除和插入值。
我想要一个名为 的表restrictions_deleted,从中删除的每一行都restrictions将自动存储。由于restrictions具有序列号,因此不会有重复项。
如何在 PostgreSQL 中编写这样的触发器?
我目前正在尝试使用 PL/pgSQL,想知道是否有更优雅的方法来做这样的事情:
select c.data into data from doc c where c.doc_id = id and c.group_cur > group_cur order by c.id desc limit 1;
EXCEPTION
WHEN NO_DATA_FOUND THEN
select c.data into data from doc c where c.doc_id = id and c.global_cur > global_cur order by c.id desc limit 1;
EXCEPTION
WHEN NO_DATA_FOUND THEN
RETURN NULL;
Run Code Online (Sandbox Code Playgroud) 任何人都可以总结以下之间的区别:
http://www.postgresql.org/docs/9.1/static/xfunc-sql.html
和
http://www.postgresql.org/docs/9.1/static/plpgsql.html
?
要点:
鉴于当前 Postgres 9.4 中的此设置(来自此相关问题):
CREATE TABLE foo (ts, foo) AS
VALUES (1, 'A') -- int, text
, (7, 'B');
CREATE TABLE bar (ts, bar) AS
VALUES (3, 'C')
, (5, 'D')
, (9, 'E');
Run Code Online (Sandbox Code Playgroud)
db<> fiddle here(也来自上一个问题)。
我SELECT用 a写了一个FULL JOIN来实现引用问题的目标。简化:
SELECT ts, f.foo, b.bar
FROM foo f
FULL JOIN bar b USING (ts);Run Code Online (Sandbox Code Playgroud)
As per specifications, the correct way to address the column ts is without table qualification. Either of the …
我正在尝试使用 RECORD 数据类型返回多个记录,有没有一种方法可以附加到 RECORD 并在每次迭代时向该 RECORD 添加/附加一个新值。
也就是说,我要追加到rec使rec成为一组行,当循环结束,我可以只返回在我的函数结束。目前,我正在这样做 -
SELECT temp_table.col1, temp_table.col2, temp_table.col3
INTO rec
FROM temp_table
WHERE temp_table.col3 = false;
Run Code Online (Sandbox Code Playgroud)
我的完整代码在这里:
CREATE OR REPLACE FUNCTION validation()
RETURNS RECORD AS $$
DECLARE
rec RECORD;
temp_row RECORD;
BEGIN
CREATE TEMPORARY TABLE temp_table (col1 TEXT, col2 INTEGER, col3 BOOLEAN) ON COMMIT DROP;
FOR temp_row IN SELECT * FROM staging.validation
LOOP
RAISE NOTICE 'sql: %', temp_row.sql;
EXECUTE format('INSERT INTO temp_table %s', temp_row.sql);
IF (SELECT DISTINCT temp_table.col3 FROM temp_table WHERE …Run Code Online (Sandbox Code Playgroud) 我们在 Postgres 中有一个 try catch 等价物吗?我编写了一些由触发器调用的用户定义函数。我(不想)想忽略错误,以免流程中断。
根据文档:
CONCURRENTLY 刷新物化视图而不锁定物化视图上的并发选择。(……)
... 其他内容 ...
即使使用此选项,一次也只能针对任何 一个物化视图运行一个 REFRESH。
我有一个函数可以检查 MATERIALIZED VIEW 的上次刷新时间,如果超过 60 秒,它会刷新它。
但是,如果我尝试同时从两个单独的进程刷新物化视图会发生什么?他们会排队还是会引发错误?
有没有办法检测何时刷新 MATERIALIZED VIEW 从而避免触摸它?
目前,我已经在刷新(设置refreshing为true)之前填充表记录,然后false在过程完成时将其设置为。
EXECUTE 'INSERT INTO refresh_status (last_update, refreshing)
VALUES (clock_timestamp(), true) RETURNING id') INTO refresh_id;
EXECUTE 'REFRESH MATERIALIZED VIEW CONCURRENTLY my_mat_view';
EXECUTE 'UPDATE refresh_status SET refreshing=false WHERE id=$1' USING refresh_id;
Run Code Online (Sandbox Code Playgroud)
然后,每当我调用此过程时,我都会检查最新的last_update及其refreshing值。如果refreshing为 true,则不要尝试刷新物化视图。
EXECUTE 'SELECT
extract(epoch FROM now() - (last_update))::integer,
refreshing
FROM refresh_status
ORDER BY …Run Code Online (Sandbox Code Playgroud) 我有一个 Web 服务(http api),它允许用户安静地创建资源。在身份验证和验证之后,我将数据传递给 Postgres 函数,并允许它检查授权并在数据库中创建记录。
我今天发现了一个错误,即在同一秒内发出了两个 http 请求,导致使用相同的数据两次调用此函数。函数内部有一个子句,它在表上进行选择以查看值是否存在,如果存在,则获取 ID 并在下一个操作中使用该 ID,如果不存在,则插入数据,获取返回 ID,然后在下一个操作中使用它。下面是一个简单的例子。
select id into articleId from articles where title = 'my new blog';
if articleId is null then
insert into articles (title, content) values (_title, _content)
returning id into articleId;
end if;
-- Continue, using articleId to represent the article for next operations...
Run Code Online (Sandbox Code Playgroud)
正如您可能猜到的那样,我对数据进行了幻读,其中两个事务都进入了if articleId is null then块并试图插入到表中。一个成功了,另一个失败了,因为一个领域的独特限制。
我已经环顾四周,看看如何抵御这种情况,并找到了一些不同的选择,但由于某些原因,它们似乎都不适合我们的需求,我正在努力寻找任何替代方案。
insert ... on conflict do nothing/update...我首先查看了on conflict看起来不错的选项,但是唯一的选项是do nothing不返回导致冲突的记录的 ID,并且do update不会工作,因为它会导致触发器在实际数据时被触发没有改变。在某些情况下,这不是问题,但在许多情况下,这可能会使会话用户会话无效,这是我们无法做到的。 …当 PostgreSQL 抛出异常时,有一行“CONTEXT”,如:
ERROR: INSERT has more target COLUMNS than expressions
LINE 3: ...
^
QUERY: INSERT INTO ...
CONTEXT: PL/pgSQL FUNCTION "XXXXX" line 4 at SQL statement
Run Code Online (Sandbox Code Playgroud)
但是当我抛出异常时,这条线不存在。我没有找到如何添加它。
RAISE EXCEPTION 'blablabla' USING HINT = 'blablablabla';
Run Code Online (Sandbox Code Playgroud)
是否可以将此行添加到我的异常中?
plpgsql ×10
postgresql ×10
concurrency ×1
delete ×1
join ×1
parameter ×1
plpython ×1
transaction ×1
trigger ×1
upsert ×1