[英]PostgreSQL and JDBC: Is `UPDATE table … RETURNING … INTO` supported?
我有一个带有 [主键计数器] 的表,用于 [另一个表中的每页注释]。
这些主键是每页的:对于每一页,评论 ID 从 1 开始。
我想自动分配 10 个 ID 来写 10 个新评论。
— 我可以用 PostgreSQL 和 JDBC 做到这一点吗?
(您是否有任何示例/相关 JDBC 文档的链接?)
我只找到了关于如何使用一些getGeneratedKeys
returning
新插入行的主键的示例,这在我的情况下似乎没有用。
***
我认为 SQL UPDATE 语句看起来像这样:
update PAGES
set NEXT_COMMENT_ID = NEXT_COMMENT_ID + 10
where PAGE_ID = ? <-- next-comment-id is *per page*
returning NEXT_COMMENT_ID into ?
因此,不同的线程和服务器不会尝试重用/覆盖相同的 ID(对吗?)。
无需在Statement
对象上使用execute()
和getResult()
方法即可支持此操作:
像这样的东西(不包括任何错误处理):
String sql = "update ... returning ...";
boolean hasResult = statement.execute(sql);
int affectedRows = 0;
ResultSet rs = null;
if (hasResult) {
rs = statement.getResultSet();
}
int affectedRows = statement.getUpdateCount();
正如您知道该语句的作用,这应该没问题。 处理“未知”SQL 语句有点复杂,因为您需要在循环中调用getMoreResults()
和getUpdateCount()
。 有关详细信息,请参阅 Javadoc。
所以你想要以下结构?:
x = 页面主键 y = 评论主键
页表
x
-
1
2
3
4 etc
评论表
x y
- -
1 1
1 2
1 3
1 4
2 1
2 2
2 3
etc?
在这里有一个外键结构对子记录有上限是最有意义的。
创建一个存储函数,它会update ... returning ... into
工作:
create or replace function INC_NEXT_PER_PAGE_REPLY_ID(
site_id varchar(32), page_id varchar(32), step int) returns int as $$
declare
next_id int;
begin
update DW1_PAGES
set NEXT_REPLY_ID = NEXT_REPLY_ID + step
where SITE_ID = site_id and PAGE_ID = page_id
returning NEXT_REPLY_ID into next_id;
return next_id;
end;
$$ language plpgsql;
并像这样调用它:
statement = connection.prepareCall(
"{? = call INC_NEXT_PER_PAGE_REPLY_ID(?, ?, ?) }")
statement.registerOutParameter(1, java.sql.Types.INTEGER)
bind(values, statement, firstBindPos = 2) // bind pos no. 1 is the return value
statement.execute()
nextNewReplyIdAfterwards = statement.getInt(1)
相关文档:
要使表包含逻辑顺序,您可能需要在子表中创建一个复合键和一个外键。
sd=# create table x (x int);
CREATE TABLE
sd=# create table y (x int, y int);
CREATE TABLE
sd=# alter table x add primary key (x);
NOTICE: ALTER TABLE / ADD PRIMARY KEY will create implicit index "x_pkey" for table "x"
ALTER TABLE
sd=# alter table y add foreign key (x) references x (x);
ALTER TABLE
sd=# alter table y add primary key (x,y);
NOTICE: ALTER TABLE / ADD PRIMARY KEY will create implicit index "y_pkey" for table "y"
ALTER TABLE
sd=# insert into x values (1);
INSERT 0 1
sd=# insert into x values (2);
INSERT 0 1
sd=# insert into x values (3);
INSERT 0 1
sd=# insert into y values (1,1);
INSERT 0 1
sd=# insert into y values (1,2);
INSERT 0 1
sd=# insert into y values (1,3);
INSERT 0 1
sd=# insert into y values (1,1);
ERROR: duplicate key value violates unique constraint "y_pkey"
DETAIL: Key (x, y)=(1, 1) already exists.
sd=# select * from x;
x
---
1
2
3
(3 rows)
sd=# select * from y;
x | y
---+---
1 | 1
1 | 2
1 | 3
(3 rows)
这应该能让你到达你想去的地方吗?
您正在执行更新,但语句会生成结果,因此请使用executeQuery()
而不是executeUpdate()
。 这就是调用之间的真正区别: executeQuery()
处理产生ResultSet
语句; 而executeUpdate()
返回受影响的行数的计数。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.