小编Joi*_*dio的帖子

INSERT 使用 CTE INSERT 的结果提供唯一的 id 值

我正在写一份工作,将数据从旧设计转换为新设计。在这个过程中,我需要将 id 从插入到一个单独的表中,并在插入到目标表中使用它,如下所示:

CREATE TABLE t1 {
  t1_id BIGSERIAL,
  col1 VARCHAR
};
CREATE TABLE t2 {
  t2_id BIGSERIAL,
  col2 VARCHAR, -- renamed from col1 to avoid confusion
  t1_id BIGINT REFERENCES t1.t1_id
};
Run Code Online (Sandbox Code Playgroud)

我定义了与以下形式匹配的 SQL:

WITH ins AS (
  INSERT INTO t1 (t1_id) VALUES (DEFAULT) RETURNING t1_id
) INSERT INTO t2
  (col1, t1_id)
SELECT
  a.val1, (SELECT * FROM ins)
FROM t3 a;
Run Code Online (Sandbox Code Playgroud)

我希望它为.. 的SELECT * FROM ins每一行运行SELECT.. 但它只运行一次,并将该值用于SELECT.. 如何重构我的 SQL 以获得所需的行为?

编辑4

t1 最终看起来像:

1,<NULL> …
Run Code Online (Sandbox Code Playgroud)

postgresql postgresql-9.2

12
推荐指数
1
解决办法
1万
查看次数

如何确定列是否定义为串行数据类型而不是基于目录的整数?

所以我目前正在创建一些 SQL 来读取 postgres (9.1) 目录以构建表定义。但是,我遇到了 SERIAL/BIGSERIAL 数据类型的问题。

例子:

CREATE TABLE cruft.temp ( id BIGSERIAL PRIMARY KEY );
SELECT * FROM information_schema.columns WHERE table_schema='cruft' AND table_name='temp';
"db","cruft","temp","id",1,"nextval('cruft.temp_id_seq'::regclass)","NO","bigint",,,64,2,0,,,,,,,,,,,,,"db","pg_catalog","int8",,,,,"1","NO","NO",,,,,,,"NEVER",,"YES"
Run Code Online (Sandbox Code Playgroud)

它给了我数据库名 (db)、模式名 (cruft)、表名 (temp)、列名 (id)、默认值 (nextval( ... )) 和数据类型(bigint 和 int8 .. NOT bigserial) ...我意识到我可以检查默认值是否是一个序列 - 但我不相信这会是 100% 准确的,因为我可以手动创建一个序列并创建一个非序列列,其中默认值是那个顺序。

有没有人对我如何实现这一点有建议?除了检查 nextval(*_seq) 的默认值之外还有什么别的方法吗?

针对 TL;DR 或不熟悉 pg_catalog 的新用户在此处添加的 SQL 解决方案进行了编辑:

with sequences as (
  select oid, relname as sequencename from pg_class where relkind = 'S'
) select
  sch.nspname as schemaname, tab.relname as tablename, col.attname …
Run Code Online (Sandbox Code Playgroud)

postgresql

9
推荐指数
2
解决办法
1万
查看次数

标签 统计

postgresql ×2

postgresql-9.2 ×1