把“章节正文 + 图片”从 chapters 单表/JSON 结构,重构为“章节 chapter + 段落 section + 图片 memoir_images 独立表”的新数据模型,同时联动修改接口、PDF 导出、异步任务、迁移脚本、测试,以及修复 Android 端聊天列表显示问题。 (#9)
* refactor: 表结构重构,新增段落section和图片image新表 * fix: fix android app import error * refactor: 重构文件名 * fix: 优化提示词 * fix: 消息气泡显示位置异常问题 --------- Co-authored-by: yangshilin <2157598560@qq.com>
This commit is contained in:
@@ -47,7 +47,7 @@ import signal
|
||||
from sqlalchemy import create_engine, select
|
||||
from sqlalchemy.orm import sessionmaker, Session
|
||||
|
||||
from database.models import Base, User, Conversation, Segment, Chapter, Book, MemoirState
|
||||
from database.models import Base, User, Conversation, Segment, Chapter, ChapterSection, Book, MemoirState
|
||||
from services.llm_service import LLMService
|
||||
from agents.state_schema import MemoirStateSchema, SlotData, default_state
|
||||
from agents.prompts.memory_prompts import (
|
||||
@@ -57,6 +57,7 @@ from agents.prompts.memory_prompts import (
|
||||
inject_image_placeholder_template,
|
||||
STAGE_TO_ORDER,
|
||||
)
|
||||
from services.memoir_images.parser import split_narrative_to_sections
|
||||
|
||||
logging.basicConfig(
|
||||
level=logging.INFO,
|
||||
@@ -350,23 +351,35 @@ def cmd_preview(phone: str, batch_size: int, skip_llm_slots: bool):
|
||||
nickname = user.nickname
|
||||
logger.info(f"用户: {nickname} (id={user_id})")
|
||||
|
||||
# 读取现有 active 章节
|
||||
# 读取现有 active 章节(含 sections,正文从 sections 拼接)
|
||||
from sqlalchemy.orm import joinedload
|
||||
old_chapters = (
|
||||
db.execute(
|
||||
select(Chapter)
|
||||
.where(Chapter.user_id == user_id, Chapter.is_active == True)
|
||||
.options(joinedload(Chapter.sections))
|
||||
.order_by(Chapter.order_index)
|
||||
)
|
||||
.unique()
|
||||
.scalars()
|
||||
.all()
|
||||
)
|
||||
old_chapter_data = []
|
||||
for ch in old_chapters:
|
||||
content = ""
|
||||
if getattr(ch, "sections", None):
|
||||
content = "\n\n".join(
|
||||
(s.content or "").strip()
|
||||
for s in sorted(ch.sections, key=lambda x: x.order_index)
|
||||
if (s.content or "").strip()
|
||||
)
|
||||
content_len = len(content)
|
||||
content_preview = (content[:200] + "…") if content_len > 200 else content
|
||||
old_chapter_data.append({
|
||||
"category": ch.category,
|
||||
"title": ch.title,
|
||||
"content_len": len(ch.content) if ch.content else 0,
|
||||
"content_preview": (ch.content[:200] + "…") if ch.content and len(ch.content) > 200 else (ch.content or ""),
|
||||
"content_len": content_len,
|
||||
"content_preview": content_preview,
|
||||
})
|
||||
logger.info(f"现有章节: {len(old_chapters)} 个")
|
||||
|
||||
@@ -562,7 +575,7 @@ def cmd_apply(phone: str):
|
||||
slots={k: {sk: sv.model_dump() for sk, sv in v.items()} for k, v in ds.slots.items()},
|
||||
))
|
||||
|
||||
# 4. 插入新章节
|
||||
# 4. 插入新章节(无 content/images;正文与配图写入 chapter_sections)
|
||||
last_chapter_id = None
|
||||
for ch_data in new_chapters:
|
||||
ch_id = str(uuid.uuid4())
|
||||
@@ -570,15 +583,34 @@ def cmd_apply(phone: str):
|
||||
id=ch_id,
|
||||
user_id=user_id,
|
||||
title=ch_data["title"],
|
||||
content=ch_data["content"],
|
||||
order_index=ch_data["order_index"],
|
||||
status="completed",
|
||||
category=ch_data["category"],
|
||||
images=[],
|
||||
cover_image=None,
|
||||
is_new=True,
|
||||
source_segments=ch_data.get("source_segment_ids", []),
|
||||
)
|
||||
db.add(chapter)
|
||||
db.flush()
|
||||
content = ch_data.get("content") or ""
|
||||
sections = split_narrative_to_sections(content)
|
||||
if not sections:
|
||||
db.add(ChapterSection(
|
||||
id=str(uuid.uuid4()).replace("-", "")[:32],
|
||||
chapter_id=ch_id,
|
||||
order_index=0,
|
||||
content=content.strip(),
|
||||
image=None,
|
||||
))
|
||||
else:
|
||||
for order_idx, seg in enumerate(sections):
|
||||
db.add(ChapterSection(
|
||||
id=str(uuid.uuid4()).replace("-", "")[:32],
|
||||
chapter_id=ch_id,
|
||||
order_index=order_idx,
|
||||
content=(seg.get("content") or "").strip(),
|
||||
image=None,
|
||||
))
|
||||
last_chapter_id = ch_id
|
||||
logger.info(f" 新建章节: [{ch_data['category']}] {ch_data['title']} — {ch_data['content_len']} 字")
|
||||
|
||||
|
||||
Reference in New Issue
Block a user