221 lines
9.2 KiB
PL/PgSQL
221 lines
9.2 KiB
PL/PgSQL
-- =============================================================================
|
||
-- 镭射卡重构 v3 — 业务表迁移(Phase 1)
|
||
-- 文档:docs/specs/2026-05-25-laser-card-refactor-design.md §6.5–6.11
|
||
-- 创建日期:2026-05-27
|
||
--
|
||
-- 说明:
|
||
-- 1. 本期新增 laser_card_templates / laser_card_instances / laser_card_operation_logs
|
||
-- 2. 不对 assets / asset_registry 做 ALTER(品类+工艺走 assets.tags 约定,见 §6.3.1)
|
||
-- 3. 依赖:public.assets、public.mint_orders、public.materials 已存在
|
||
-- 执行:psql -U <user> -d <db> -f migrate_laser_card_v3_tables.sql
|
||
-- 备注:§4 含全部 COMMENT ON(表/字段/索引/约束),可重复执行;已建表无备注时可单独跑 migrate_laser_card_v3_comments_only.sql
|
||
-- =============================================================================
|
||
|
||
BEGIN;
|
||
|
||
-- -----------------------------------------------------------------------------
|
||
-- 1. laser_card_templates
|
||
-- -----------------------------------------------------------------------------
|
||
CREATE TABLE IF NOT EXISTS public.laser_card_templates (
|
||
id BIGSERIAL PRIMARY KEY,
|
||
template_code VARCHAR(64) NOT NULL,
|
||
name VARCHAR(100) NOT NULL,
|
||
description TEXT,
|
||
status VARCHAR(20) NOT NULL DEFAULT 'published',
|
||
version INT NOT NULL DEFAULT 1,
|
||
thumbnail_oss_key VARCHAR(255),
|
||
backdrop_options JSONB NOT NULL DEFAULT '[]'::jsonb,
|
||
render_config JSONB NOT NULL DEFAULT '{}'::jsonb,
|
||
engine_min_version VARCHAR(32) NOT NULL DEFAULT 'compositor-1.0.0',
|
||
sort_order INT NOT NULL DEFAULT 0,
|
||
star_id BIGINT NOT NULL DEFAULT 0,
|
||
created_by BIGINT NOT NULL DEFAULT 0,
|
||
created_at BIGINT NOT NULL,
|
||
updated_at BIGINT NOT NULL,
|
||
deleted_at BIGINT
|
||
);
|
||
|
||
CREATE UNIQUE INDEX IF NOT EXISTS uk_lct_code_version
|
||
ON public.laser_card_templates (template_code, version)
|
||
WHERE deleted_at IS NULL;
|
||
|
||
CREATE INDEX IF NOT EXISTS idx_lct_status_star
|
||
ON public.laser_card_templates (status, star_id)
|
||
WHERE deleted_at IS NULL;
|
||
|
||
-- -----------------------------------------------------------------------------
|
||
-- 2. laser_card_instances
|
||
-- -----------------------------------------------------------------------------
|
||
CREATE TABLE IF NOT EXISTS public.laser_card_instances (
|
||
id BIGSERIAL PRIMARY KEY,
|
||
instance_no VARCHAR(32) NOT NULL,
|
||
instance_ulid VARCHAR(40) NOT NULL,
|
||
template_id BIGINT NOT NULL,
|
||
template_code VARCHAR(64) NOT NULL,
|
||
template_version INT NOT NULL,
|
||
owner_user_id BIGINT NOT NULL,
|
||
star_id BIGINT NOT NULL,
|
||
status VARCHAR(20) NOT NULL DEFAULT 'rendered',
|
||
client_request_id VARCHAR(64),
|
||
render_config JSONB,
|
||
materials_snapshot JSONB NOT NULL DEFAULT '[]'::jsonb,
|
||
composite_oss_key VARCHAR(255),
|
||
composite_material_id BIGINT,
|
||
asset_id BIGINT,
|
||
mint_order_id VARCHAR(100),
|
||
idempotency_key VARCHAR(64),
|
||
version INT NOT NULL DEFAULT 1,
|
||
created_at BIGINT NOT NULL,
|
||
updated_at BIGINT NOT NULL,
|
||
deleted_at BIGINT,
|
||
|
||
CONSTRAINT fk_lci_template
|
||
FOREIGN KEY (template_id) REFERENCES public.laser_card_templates (id),
|
||
CONSTRAINT fk_lci_asset
|
||
FOREIGN KEY (asset_id) REFERENCES public.assets (id) ON DELETE SET NULL,
|
||
CONSTRAINT fk_lci_mint_order
|
||
FOREIGN KEY (mint_order_id) REFERENCES public.mint_orders (order_id) ON DELETE SET NULL,
|
||
CONSTRAINT fk_lci_composite_material
|
||
FOREIGN KEY (composite_material_id) REFERENCES public.materials (id) ON DELETE SET NULL,
|
||
CONSTRAINT chk_lci_status
|
||
CHECK (status IN ('rendered', 'minting', 'minted'))
|
||
);
|
||
|
||
CREATE UNIQUE INDEX IF NOT EXISTS uk_lci_instance_no
|
||
ON public.laser_card_instances (instance_no);
|
||
|
||
CREATE UNIQUE INDEX IF NOT EXISTS uk_lci_instance_ulid
|
||
ON public.laser_card_instances (instance_ulid);
|
||
|
||
CREATE UNIQUE INDEX IF NOT EXISTS uk_lci_user_client_req
|
||
ON public.laser_card_instances (owner_user_id, client_request_id)
|
||
WHERE deleted_at IS NULL AND client_request_id IS NOT NULL;
|
||
|
||
CREATE INDEX IF NOT EXISTS idx_lci_owner_status
|
||
ON public.laser_card_instances (owner_user_id, status)
|
||
WHERE deleted_at IS NULL;
|
||
|
||
CREATE INDEX IF NOT EXISTS idx_lci_asset
|
||
ON public.laser_card_instances (asset_id)
|
||
WHERE asset_id IS NOT NULL AND deleted_at IS NULL;
|
||
|
||
CREATE INDEX IF NOT EXISTS idx_lci_star_created
|
||
ON public.laser_card_instances (star_id, created_at DESC)
|
||
WHERE deleted_at IS NULL;
|
||
|
||
-- -----------------------------------------------------------------------------
|
||
-- 3. laser_card_operation_logs
|
||
-- -----------------------------------------------------------------------------
|
||
CREATE TABLE IF NOT EXISTS public.laser_card_operation_logs (
|
||
id BIGSERIAL PRIMARY KEY,
|
||
instance_id BIGINT NOT NULL,
|
||
instance_no VARCHAR(32) NOT NULL,
|
||
operator_user_id BIGINT NOT NULL,
|
||
action VARCHAR(50) NOT NULL,
|
||
status_before VARCHAR(20),
|
||
status_after VARCHAR(20),
|
||
request_id VARCHAR(64),
|
||
payload_json JSONB,
|
||
result_json JSONB,
|
||
ip_address VARCHAR(45),
|
||
user_agent VARCHAR(255),
|
||
latency_ms INT,
|
||
err_code VARCHAR(32),
|
||
created_at BIGINT NOT NULL,
|
||
|
||
CONSTRAINT fk_lclog_instance
|
||
FOREIGN KEY (instance_id) REFERENCES public.laser_card_instances (id) ON DELETE CASCADE
|
||
);
|
||
|
||
CREATE INDEX IF NOT EXISTS idx_lclog_instance_time
|
||
ON public.laser_card_operation_logs (instance_id, created_at DESC);
|
||
|
||
CREATE INDEX IF NOT EXISTS idx_lclog_operator_time
|
||
ON public.laser_card_operation_logs (operator_user_id, created_at DESC);
|
||
|
||
CREATE INDEX IF NOT EXISTS idx_lclog_action_time
|
||
ON public.laser_card_operation_logs (action, created_at DESC);
|
||
|
||
-- -----------------------------------------------------------------------------
|
||
-- 4. 表 / 字段 / 索引 / 约束备注(COMMENT,可重复执行)
|
||
-- -----------------------------------------------------------------------------
|
||
\ir migrate_laser_card_v3_comments.sql
|
||
|
||
-- -----------------------------------------------------------------------------
|
||
-- 5. 种子数据:5 套预设(与 frontend/utils/laser-card/laserPresets.js 对齐)
|
||
-- -----------------------------------------------------------------------------
|
||
INSERT INTO public.laser_card_templates (
|
||
template_code,
|
||
name,
|
||
status,
|
||
version,
|
||
backdrop_options,
|
||
render_config,
|
||
engine_min_version,
|
||
sort_order,
|
||
star_id,
|
||
created_by,
|
||
created_at,
|
||
updated_at
|
||
)
|
||
SELECT
|
||
v.template_code,
|
||
v.name,
|
||
'published',
|
||
1,
|
||
v.backdrop_options::jsonb,
|
||
v.render_config::jsonb,
|
||
'compositor-1.0.0',
|
||
v.sort_order,
|
||
0,
|
||
0,
|
||
(EXTRACT(EPOCH FROM clock_timestamp()) * 1000)::bigint,
|
||
(EXTRACT(EPOCH FROM clock_timestamp()) * 1000)::bigint
|
||
FROM (
|
||
VALUES
|
||
(
|
||
'dream',
|
||
'梦幻',
|
||
0,
|
||
'[{"id":"liquidBlue","label":"液态蓝","oss_key":"static/laser-bg/laser-bg-1.png"}]',
|
||
'{"style":"dream","angle":36,"beam":"prism","backdrop":"liquidBlue","laserStrength":78,"diffractionDensity":68,"marbleFlow":52,"beamIntensity":92,"grainDensity":82}'
|
||
),
|
||
(
|
||
'classic',
|
||
'经典',
|
||
1,
|
||
'[{"id":"liquidLavender","label":"液态紫","oss_key":"static/laser-bg/laser-bg-2.png"}]',
|
||
'{"style":"classic","angle":24,"beam":"aurora","backdrop":"liquidLavender","laserStrength":85,"diffractionDensity":74,"marbleFlow":38,"beamIntensity":96,"grainDensity":76}'
|
||
),
|
||
(
|
||
'holoFull',
|
||
'全息',
|
||
2,
|
||
'[{"id":"liquidPearl","label":"液态珍珠","oss_key":"static/laser-bg/laser-bg-3.png"}]',
|
||
'{"style":"holoFull","angle":58,"beam":"neon","backdrop":"liquidPearl","laserStrength":90,"diffractionDensity":80,"marbleFlow":58,"beamIntensity":100,"grainDensity":88}'
|
||
),
|
||
(
|
||
'ice',
|
||
'冰蓝',
|
||
3,
|
||
'[{"id":"liquidBlue","label":"液态蓝","oss_key":"static/laser-bg/laser-bg-1.png"}]',
|
||
'{"style":"ice","angle":46,"beam":"white","backdrop":"liquidBlue","laserStrength":72,"diffractionDensity":60,"marbleFlow":44,"beamIntensity":88,"grainDensity":74}'
|
||
),
|
||
(
|
||
'sunset',
|
||
'晚霞',
|
||
4,
|
||
'[{"id":"liquidLavender","label":"液态紫","oss_key":"static/laser-bg/laser-bg-2.png"}]',
|
||
'{"style":"sunset","angle":30,"beam":"sunset","backdrop":"liquidLavender","laserStrength":82,"diffractionDensity":66,"marbleFlow":50,"beamIntensity":94,"grainDensity":84}'
|
||
)
|
||
) AS v (template_code, name, sort_order, backdrop_options, render_config)
|
||
WHERE NOT EXISTS (
|
||
SELECT 1
|
||
FROM public.laser_card_templates t
|
||
WHERE t.template_code = v.template_code
|
||
AND t.version = 1
|
||
AND t.deleted_at IS NULL
|
||
);
|
||
|
||
COMMIT;
|