feat: 内容表 *_pinyin 列迁移(幂等 EnsureColumn)

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
This commit is contained in:
2026-08-13 13:46:11 +08:00
co-authored by Claude Opus 4.7
parent 45e52af14b
commit 568ffde0ce
6 changed files with 56 additions and 4 deletions
+4
View File
@@ -19,12 +19,16 @@ CREATE TABLE IF NOT EXISTS element (
id INTEGER PRIMARY KEY AUTOINCREMENT,
e_type INTEGER NOT NULL,
name TEXT NOT NULL,
name_pinyin TEXT,
image TEXT,
audio TEXT,
description TEXT,
description_pinyin TEXT,
status INTEGER NOT NULL DEFAULT 1,
sort_order INTEGER NOT NULL DEFAULT 1
);
CREATE INDEX IF NOT EXISTS idx_element_type ON element(e_type);`)
common.EnsureColumn(ctx, consts.TableElement, "name_pinyin", "TEXT")
common.EnsureColumn(ctx, consts.TableElement, "description_pinyin", "TEXT")
return err
}
+2
View File
@@ -21,6 +21,7 @@ CREATE TABLE IF NOT EXISTS level (
title TEXT NOT NULL,
scene_id INTEGER,
scene_content TEXT NOT NULL,
scene_content_pinyin TEXT,
scene_image TEXT,
scene_audio TEXT,
age_group TEXT NOT NULL DEFAULT '4-6',
@@ -29,5 +30,6 @@ CREATE TABLE IF NOT EXISTS level (
status INTEGER NOT NULL DEFAULT 1
);
CREATE INDEX IF NOT EXISTS idx_level_strategy ON level(strategy_id, sort_order);`)
common.EnsureColumn(ctx, consts.TableLevel, "scene_content_pinyin", "TEXT")
return err
}
+8
View File
@@ -19,14 +19,22 @@ CREATE TABLE IF NOT EXISTS node_option (
id INTEGER PRIMARY KEY AUTOINCREMENT,
node_id INTEGER NOT NULL,
text TEXT NOT NULL,
text_pinyin TEXT,
prop_id INTEGER,
audio TEXT,
next_node_id INTEGER,
feedback TEXT NOT NULL,
feedback_pinyin TEXT,
feedback_pros TEXT, -- 对比点评:好处
feedback_cons TEXT, -- 对比点评:不足/错过的更好选择
feedback_audio TEXT,
sort_order INTEGER NOT NULL DEFAULT 1,
status INTEGER NOT NULL DEFAULT 1
);
CREATE INDEX IF NOT EXISTS idx_option_node ON node_option(node_id);`)
common.EnsureColumn(ctx, consts.TableNodeOption, "text_pinyin", "TEXT")
common.EnsureColumn(ctx, consts.TableNodeOption, "feedback_pinyin", "TEXT")
common.EnsureColumn(ctx, consts.TableNodeOption, "feedback_pros", "TEXT")
common.EnsureColumn(ctx, consts.TableNodeOption, "feedback_cons", "TEXT")
return err
}
+2
View File
@@ -21,6 +21,7 @@ CREATE TABLE IF NOT EXISTS scene_node (
title TEXT,
character_id INTEGER,
content TEXT NOT NULL,
content_pinyin TEXT,
image TEXT,
audio TEXT,
node_type INTEGER NOT NULL DEFAULT 1,
@@ -32,5 +33,6 @@ CREATE TABLE IF NOT EXISTS scene_node (
status INTEGER NOT NULL DEFAULT 1
);
CREATE INDEX IF NOT EXISTS idx_node_level ON scene_node(level_id);`)
common.EnsureColumn(ctx, consts.TableSceneNode, "content_pinyin", "TEXT")
return err
}
+12 -4
View File
@@ -21,12 +21,16 @@ CREATE TABLE IF NOT EXISTS strategy (
pinyin TEXT NOT NULL,
group_no INTEGER NOT NULL,
group_name TEXT NOT NULL,
meaning TEXT NOT NULL,
teach_content TEXT,
meaning TEXT NOT NULL, -- 儿童语言释义
meaning_pinyin TEXT, -- 释义拼音(逐字对齐 JSON)
teach_content TEXT, -- 计策学堂:儿童化讲解(名称/释义/使用时机)
teach_content_pinyin TEXT,
teach_image TEXT,
teach_audio TEXT,
summary_q TEXT,
summary_options TEXT,
summary_q TEXT, -- 智慧总结反思题
summary_q_pinyin TEXT,
summary_options TEXT, -- 反思题选项 JSON(含正确答案)
summary_options_pinyin TEXT,
summary_audio TEXT,
icon TEXT,
sort_order INTEGER NOT NULL,
@@ -34,5 +38,9 @@ CREATE TABLE IF NOT EXISTS strategy (
status INTEGER NOT NULL DEFAULT 1
);
CREATE INDEX IF NOT EXISTS idx_strategy_group ON strategy(group_no, sort_order);`)
common.EnsureColumn(ctx, consts.TableStrategy, "meaning_pinyin", "TEXT")
common.EnsureColumn(ctx, consts.TableStrategy, "teach_content_pinyin", "TEXT")
common.EnsureColumn(ctx, consts.TableStrategy, "summary_q_pinyin", "TEXT")
common.EnsureColumn(ctx, consts.TableStrategy, "summary_options_pinyin", "TEXT")
return err
}
+28
View File
@@ -0,0 +1,28 @@
package common
import (
"context"
"fmt"
"github.com/gogf/gf/v2/frame/g"
)
// EnsureColumn 幂等加列:PRAGMA 查列不存在则 ALTER TABLE ADD COLUMN。
// 失败只记警告,不阻断启动(列缺失时后续查询只会取到空值)。
func EnsureColumn(ctx context.Context, table, col, sqlType string) {
cols, err := g.DB().GetAll(ctx, fmt.Sprintf("PRAGMA table_info(%s)", table))
if err != nil {
g.Log().Warningf(ctx, "migrate: %s 表结构读取失败: %v", table, err)
return
}
for _, c := range cols {
if c["name"].String() == col {
return
}
}
if _, err := g.DB().Exec(ctx, fmt.Sprintf("ALTER TABLE %s ADD COLUMN %s %s", table, col, sqlType)); err != nil {
g.Log().Warningf(ctx, "migrate: %s.%s 加列失败: %v", table, col, err)
return
}
g.Log().Infof(ctx, "migrate: %s.%s 已添加", table, col)
}