对于 table A 中的每个现有行,在 table B 中插入 N 行
For each existing row in table A, insert N rows in table B
我正在尝试使用 SQL 编写迁移脚本。
我很容易涵盖 DDL 部分,但现在我必须迁移现有数据,如下所示:
迁移前:
Table 盒子
uuid
active_service_number
other BOX columns...
2869c64f-8ecb-4296-8c3b-1c72b308d59f
2
...
迁移后:
Table 盒子
uuid
other BOX columns...
2869c64f-8ecb-4296-8c3b-1c72b308d59f
...
Table BOX_SERVICE
uuid
number
state
box_uuid
6a33d57f-e02b-4d0a-b258-3cef0bb3dff7
0
INACTIVE
2869c64f-8ecb-4296-8c3b-1c72b308d59f
...
1
INACTIVE
2869c64f-8ecb-4296-8c3b-1c72b308d59f
...
2
ACTIVE
2869c64f-8ecb-4296-8c3b-1c72b308d59f
...
...
...
...
...
N
INACTIVE
2869c64f-8ecb-4296-8c3b-1c72b308d59f
总结一下
- 对于每个BOX行,我要创建正好NBOX_SERVICE行,编号从0到N。(N是预定的固定数字)
- 只有一个 BOX_SERVICE 应该将其状态设置为 ACTIVE,对应于相应 BOX 的 active_service_number(上例中为 2)的那个。
我找到了伪代码,但似乎无法将其翻译成 SQL。我尝试通过单个请求、多个请求、游标来完成。
这是我的 DDL 的样子:
CREATE TABLE BOX_SERVICE (uuid varchar(255) NOT NULL,
number int,
state varchar(255) DEFAULT 'INACTIVE',
box_uuid varchar(255),
PRIMARY KEY(uuid),
CONSTRAINT FK_BOX_BOX_SERVICE FOREIGN KEY (box_uuid)
REFERENCES BOX(uuid)
);
-- Migrate existing data
ALTER TABLE BOX DROP active_service_number
您可以使用 generate_series()
和 cross join
生成行:
select <uuid function>,
gs.n as number,
(case when gs.n = b.active_service_number then 'ACTIVE' else 'INACTIVE' end),
b.uuid as box_uuid
from box b cross join
generate_series(0, n, 1) as gs(n);
您的 Postgres 版本仅通过扩展提供 UUID。使用您用于生成 UUID 的第一列的任何方法。
CREATE EXTENSION IF NOT EXISTS "uuid-ossp";
select uuid_generate_v1(),sequence number,
(case when active_service_number=SEQUENCE THEN 'ACTIVE' ELSE 'INACTIVE' END)STATE,
UUID BOX_UUID from box CROSS JOIN (select generate_series(0,5) as sequence)t
输出:
UUID |Number|Status |Box_UUID
4b247576-8e42-11eb-80ae-1831bf6eced8|0 |INACTIVE|2869c64f-8ecb-4296-8c3b-1c72b308d59f
4b247577-8e42-11eb-80af-1831bf6eced8|1 |INACTIVE|2869c64f-8ecb-4296-8c3b-1c72b308d59f
4b247578-8e42-11eb-80b0-1831bf6eced8|2 |ACTIVE |2869c64f-8ecb-4296-8c3b-1c72b308d59f
4b247579-8e42-11eb-80b1-1831bf6eced8|3 |INACTIVE|2869c64f-8ecb-4296-8c3b-1c72b308d59f
4b24757a-8e42-11eb-80b2-1831bf6eced8|4 |INACTIVE|2869c64f-8ecb-4296-8c3b-1c72b308d59f
4b24757b-8e42-11eb-80b3-1831bf6eced8|5 |INACTIVE|2869c64f-8ecb-4296-8c3b-1c72b308d59f
我正在尝试使用 SQL 编写迁移脚本。 我很容易涵盖 DDL 部分,但现在我必须迁移现有数据,如下所示:
迁移前:
Table 盒子
uuid | active_service_number | other BOX columns... |
---|---|---|
2869c64f-8ecb-4296-8c3b-1c72b308d59f | 2 | ... |
迁移后:
Table 盒子
uuid | other BOX columns... |
---|---|
2869c64f-8ecb-4296-8c3b-1c72b308d59f | ... |
Table BOX_SERVICE
uuid | number | state | box_uuid |
---|---|---|---|
6a33d57f-e02b-4d0a-b258-3cef0bb3dff7 | 0 | INACTIVE | 2869c64f-8ecb-4296-8c3b-1c72b308d59f |
... | 1 | INACTIVE | 2869c64f-8ecb-4296-8c3b-1c72b308d59f |
... | 2 | ACTIVE | 2869c64f-8ecb-4296-8c3b-1c72b308d59f |
... | ... | ... | ... |
... | N | INACTIVE | 2869c64f-8ecb-4296-8c3b-1c72b308d59f |
总结一下
- 对于每个BOX行,我要创建正好NBOX_SERVICE行,编号从0到N。(N是预定的固定数字)
- 只有一个 BOX_SERVICE 应该将其状态设置为 ACTIVE,对应于相应 BOX 的 active_service_number(上例中为 2)的那个。
我找到了伪代码,但似乎无法将其翻译成 SQL。我尝试通过单个请求、多个请求、游标来完成。
这是我的 DDL 的样子:
CREATE TABLE BOX_SERVICE (uuid varchar(255) NOT NULL,
number int,
state varchar(255) DEFAULT 'INACTIVE',
box_uuid varchar(255),
PRIMARY KEY(uuid),
CONSTRAINT FK_BOX_BOX_SERVICE FOREIGN KEY (box_uuid)
REFERENCES BOX(uuid)
);
-- Migrate existing data
ALTER TABLE BOX DROP active_service_number
您可以使用 generate_series()
和 cross join
生成行:
select <uuid function>,
gs.n as number,
(case when gs.n = b.active_service_number then 'ACTIVE' else 'INACTIVE' end),
b.uuid as box_uuid
from box b cross join
generate_series(0, n, 1) as gs(n);
您的 Postgres 版本仅通过扩展提供 UUID。使用您用于生成 UUID 的第一列的任何方法。
CREATE EXTENSION IF NOT EXISTS "uuid-ossp";
select uuid_generate_v1(),sequence number,
(case when active_service_number=SEQUENCE THEN 'ACTIVE' ELSE 'INACTIVE' END)STATE,
UUID BOX_UUID from box CROSS JOIN (select generate_series(0,5) as sequence)t
输出:
UUID |Number|Status |Box_UUID
4b247576-8e42-11eb-80ae-1831bf6eced8|0 |INACTIVE|2869c64f-8ecb-4296-8c3b-1c72b308d59f
4b247577-8e42-11eb-80af-1831bf6eced8|1 |INACTIVE|2869c64f-8ecb-4296-8c3b-1c72b308d59f
4b247578-8e42-11eb-80b0-1831bf6eced8|2 |ACTIVE |2869c64f-8ecb-4296-8c3b-1c72b308d59f
4b247579-8e42-11eb-80b1-1831bf6eced8|3 |INACTIVE|2869c64f-8ecb-4296-8c3b-1c72b308d59f
4b24757a-8e42-11eb-80b2-1831bf6eced8|4 |INACTIVE|2869c64f-8ecb-4296-8c3b-1c72b308d59f
4b24757b-8e42-11eb-80b3-1831bf6eced8|5 |INACTIVE|2869c64f-8ecb-4296-8c3b-1c72b308d59f