合并图标规范与图集生成优化
合入 PR 137 的图标规范生成、稳定引用与图集提示词链路 保留主分支现行音效提交、Prompt 模块与结果压缩逻辑 解决 External Worker、生成提交和客户端测试冲突
This commit is contained in:
@@ -5837,7 +5837,7 @@
|
||||
## 2026-07-28 AI 游戏创作正式视觉规范与透明 spritesheet DAG
|
||||
|
||||
- 16-task 边界:继续复用现有 seed manifest 的 `art-director / design-foundation / art-asset-plan` 三个任务,不新增平行任务、会话或素材系统。`art-director` 是正式视觉规范前置:先通过 `/api/external/v1/editor/images/generations` 的 `kind=spec` 生成 `assets/art-spec.png`,并登记为 `assetKind=icon-spec`。`generationInputs.artSpec` 只是辅助结构化上下文,不能替代这张真实规范图。
|
||||
- 路由与依赖:`design-foundation` 以已登记 `assets/art-spec.png` 的 External Editor 稳定资源 ID 作为 `referenceImageSrcs` 中的视觉规范参考,通过 `/api/external/v1/editor/images/generations` 的 `kind=ui-design` 生成完整 `assets/ui-prototype.png`;`art-asset-plan` 以同一 art-spec 资源 ID 作为必填 `referenceImageSrc`,调用 `/api/external/v1/editor/icon-spritesheets/generations`,提交具体 `iconDescriptions` 与 `screenColor=auto` 生成透明 `assets/art-spritesheet.png`。严禁把 `assets/ui-prototype.png` 当作规范图引用;`art-spec.png` 缺失、不是当前画布的 `icon-spec` 或缺少稳定 `resourceId` 时,两个下游任务都必须等待 `art-director`,不得把本地路径、Data URL / Blob URL 当成稳定引用,也不得退回普通生图。单波最多 `3` 个静态职责的资源上限保持不变,调度只调整现有任务的依赖边和就绪顺序。
|
||||
- 路由与依赖:`design-foundation` 以已登记 `assets/art-spec.png` 的 External Editor 稳定资源 ID 作为 `referenceImageSrcs` 中的视觉规范参考,通过 `/api/external/v1/editor/images/generations` 的 `kind=ui-design` 生成完整 `assets/ui-prototype.png`;`art-asset-plan` 以同一 art-spec 资源 ID 作为必填 `referenceId`,调用 `/api/external/v1/editor/icon-spritesheets/generations`,提交具体 `iconDescriptions` 与 `screenColor=auto` 生成透明 `assets/art-spritesheet.png`。严禁把 `assets/ui-prototype.png` 当作规范图引用;`art-spec.png` 缺失、不是当前画布的 `icon-spec` 或缺少稳定 `resourceId` 时,两个下游任务都必须等待 `art-director`,不得把本地路径、Data URL / Blob URL 当成稳定引用,也不得退回普通生图。单波最多 `3` 个静态职责的资源上限保持不变,调度只调整现有任务的依赖边和就绪顺序。
|
||||
- UI extraction 边界:`/api/external/v1/editor/ui-designs/assets/extractions` 只适用于已有且带红框标注的 UI 设计图,不是 UI 设计图生成接口,也不进入本次 canonical DAG。后续若要生成独立 UI spritesheet,必须先补红框源图生成与正式产物合同,不得直接对无标注 `ui-prototype.png` 调用 extraction。
|
||||
- 完成门禁:External Editor 2xx 只表示生成请求完成。通用 `warning` 优先于 `sliceWarning`;`postprocess-failed-source-preserved` 表示 provider 源图是唯一权威结果,但不满足透明图集合同,客户端保留服务端事实并失败关闭,不登记本地正式 spritesheet、不伪造切片、不自动重跑。仅 `sliceWarning` 时完整透明图集有效,Runtime 把原始 reason 写入私有审计与 Agent observation,但不得声称独立切片存在。下载结果还必须解码并至少包含一个真实透明像素,纯 RGB 或全不透明 RGBA 一律拒绝落盘和 manifest 登记。
|
||||
- OpenAPI 同步事实:2026-07-28 从 `https://www.genarrative.world/api/external/v1/openapi.json` 获取的线上合同与 `docs/openapi/genarrative-external-v1.openapi.json` 原始 SHA-256 均为 `00fa39ea8781605b895b331a579fbf097eea7892962350cb2a82bed7e1024135`,逐字节一致,因此不制造无意义 JSON diff;实现按现有公开 `screenColor`、`assetLabel`、`warning` 与 `sliceWarning` 契约更新。
|
||||
@@ -6763,6 +6763,21 @@
|
||||
- 升级前 External 幂等任务可能仍在 payload 中保留客户端 references;重放比较只对白名单内已迁移的图片生成、图片修改、去背景、图标图集和 UI 提取任务,在旧侧有 references、当前侧已删除时移除旧字段,其他字段变化仍返回 `409`。音频 / 视频 / 角色动作等未迁移 job kind 始终完整比较,不能扩大兼容面。
|
||||
- 本次复用既有 `external_generation_job.dedupe_key` 唯一索引和 `spacetime-client` 查询,不改 SpacetimeDB schema、迁移或 bindings。
|
||||
|
||||
## 2026-08-05 图标规范生成拆分请求预检与最终执行,图集规范引用改为窄事务查询
|
||||
|
||||
- 图标规范 HTTP handler 在调用文本 LLM 前,先通过可复用图片请求预检完成参考图稳定性、owner 授权、Provider 配置与运行时定价校验;随后补齐 `ExtraParam` 与最终 prompt,并继续走既有 `editor_image_generation` inline / queue 分流,不新增图标规范专用 worker job。最终执行仍重新校验请求,以处理排队期间发生的权限或资源变化。
|
||||
- 图标图集主规范引用由通用 SpacetimeDB procedure `resolve_editor_reference_and_return` 在同一事务快照内解析和校验 owner。ID 使用资源 / 素材主键;objectKey 按规范化 `image_src="/<objectKey>"` 索引读取唯一行,并使用 `asset_object(bucket, object_key)` 复合索引校验对象 owner。procedure 不接收业务 / 存储类型 allowlist,复用既有 `EditorProjectResourceSnapshot` / `EditorAssetSnapshot` 返回完整单行,不新增图标专属 DTO,也不再拉取完整项目和素材库;`icon-spec` 业务类型与游戏类型由 API 业务代码校验和提取。缺失引用、跨 owner、asset object 不匹配、业务类型错误、元数据解析与数据库错误全部失败关闭;仅“合法记录没有 genre”允许返回 `None`。
|
||||
- 关联文档:`docs/【编辑器】生成类面板Lovart统一改造方案-2026-06-17.md`、`docs/【编辑器】画板图标素材生成入口设计-2026-06-15.md`、`docs/【后端架构】server-rs与SpacetimeDB数据契约-2026-05-15.md`。
|
||||
|
||||
## 2026-08-06 图标规范与图标图集使用独立任务及 ID-only 主规范引用
|
||||
|
||||
- 本条取代上一条“不新增图标规范专用 worker job”和“图标图集主规范允许 objectKey”的结论。图标规范生成使用独立 `editor_icon_spec_generation` job kind;队列保存原始强类型业务参数,worker 在统一计费操作预扣成功后执行 ExtraParam LLM、构建最终 prompt,再进入共享图片生成和既有后处理 / 持久化链。SpacetimeDB 编辑器生成结果 operation kind 白名单必须显式包含该独立 job kind,确保 Provider 成功后可以进入统一 durable receipt 原子提交;新增正式生成 job kind 时必须同步扩展白名单和模块回归。余额不足不调用文本 LLM,执行失败沿用统一退款;普通 `editor_image_generation` 的 DTO、payload 与执行行为保持不变。
|
||||
- `editor_project_icon.rs` 独立承接图标规范、图标 spritesheet、自动切片和手工拆分。普通图片模块只暴露可复用的 prompt builder 执行入口与强类型 provider 请求分流;nanobanana、无参考图 generation、有参考图 edit 的选择集中在同一个 helper,图标图集复用该 helper,不复制 provider 分支。
|
||||
- 图标规范生成的可选参考图与图标图集的必选主规范统一使用 `referenceId`,只接受当前 owner 的项目资源 ID 或账号素材 ID,不接受 objectKey、URL 或临时 key。SpacetimeDB `resolve_editor_reference_and_return` 因而只接收 `reference_id` 并按两张表主键查询,删除 `image_src` 二级索引。图标图集的普通附加参考图 `referenceImageSrcs` 仍允许 owned objectKey、项目资源 ID 或素材 ID,并继续走既有 owner 校验与真实图片下载链。
|
||||
- External v1 图标图集请求与 OpenAPI 同步改为必填 `referenceId`。前端和 Editor Agent 优先传正式 resource ID,其次传 asset ID;本地临时 ID、objectKey 和图片地址不得回退成主规范引用,未登记时明确失败并要求先上传或登记。
|
||||
- `resolve_editor_reference_and_return` 的歧义只在当前 owner 范围内判断:两张表先按 `owner_user_id` 过滤,同名但属于其它账号的行不阻断合法引用。记录存在 `asset_object_id` 时按该 ID 定位并同时核对 bucket、object key 与 owner,只有缺少 ID 的兼容旧行才按位置查询。图标规范入队 / inline 预检只验证这组行与对象元数据,最终共享图片执行器再下载一次参考图正文,避免同一引用在入队、worker 预检和生成阶段重复下载。
|
||||
- 关联:`server-rs/crates/api-server/src/editor_project_icon.rs`、`server-rs/crates/api-server/src/editor_project.rs`、`server-rs/crates/spacetime-module/src/editor_project_storage.rs`、`docs/openapi/genarrative-external-v1.openapi.json`。
|
||||
|
||||
## 2026-08-06 音效与背景音乐恢复共享音频 Composer
|
||||
|
||||
- 决策:图片画布的 `audio-sound-effect` 与 `audio-background-music` 只保留一个 `ImageCanvasAudioGenerationComposerView`,组件内以 `isSoundEffect = dialog.mode === 'audio-sound-effect'` 分流。撤销的是完整 `ImageCanvasBackgroundMusicGenerationComposerView` 这一层视图拆分,不撤销 BGM Prompt 纯模型、助手 controller、预设模型或预设跑马灯的独立职责。
|
||||
|
||||
@@ -397,7 +397,7 @@
|
||||
|
||||
- 现象:画板生成、快速编辑、图标素材或 UI 素材提取如果允许直接提交 generated objectKey,用户只要知道其他账号的私有 objectKey,就可能让 api-server 签名读取并送给外部生成供应商。
|
||||
- 原因:Data URL/Blob URL 只允许停留在浏览器临时态,正式编辑器引用必须先上传并经统一 resolver 校验归属。
|
||||
- 处理:所有私有对象引用在读取字节或签发 URL 前统一走 `resolve_editor_reference_object_key_for_owner(state, owner_user_id, source)`,先在当前账号的项目资源、素材库资产或 `asset_object` 中匹配 owner / bucket / key。只有确实需要图片字节的入口(生成 / 重绘 / 图标 / UI 提取等交给 provider 的路径)再走 `parse_editor_reference_image`(内部仍先 resolve,再下载 OSS 字节);手动去背景等只签发短期 URL 的入口不要 `parse` 整图。手动去背景还要恢复源模型时,object key 解析、所有权校验和源模型回溯必须复用同一轮账号项目 / 素材快照,项目与素材快照各最多读取一次;不得先走通用 resolver 全量读取,再为模型回溯重复拉取完整画布和素材库。图标素材等额外参考图必须真实传到 provider,不只写 metadata;图片快速编辑当前不开放额外参考图,若后续重开入口也必须沿用同一归属校验。
|
||||
- 处理:普通图片、重绘、图标图集附加参考图和 UI 提取等允许 objectKey 的私有对象引用,在读取字节或签发 URL 前统一走 `resolve_editor_reference_object_key_for_owner(state, owner_user_id, source)`,先在当前账号的项目资源、素材库资产或 `asset_object` 中匹配 owner / bucket / key。只有确实需要图片字节的入口再走 `parse_editor_reference_image`(内部仍先 resolve,再下载 OSS 字节);手动去背景等只签发短期 URL 的入口不要 `parse` 整图。图标规范生成的可选参考图与图标图集的主规范引用是更窄的业务契约:只接受正式 `referenceId`(项目资源 ID / 素材 ID),不得回退 objectKey、URL 或临时 key;图标图集的额外 `referenceImageSrcs` 才继续沿用通用 owned objectKey 规则。手动去背景还要恢复源模型时,object key 解析、所有权校验和源模型回溯必须复用同一轮账号项目 / 素材快照,项目与素材快照各最多读取一次;不得先走通用 resolver 全量读取,再为模型回溯重复拉取完整画布和素材库。图标素材等额外参考图必须真实传到 provider,不只写 metadata;图片快速编辑当前不开放额外参考图,若后续重开入口也必须沿用同一归属校验。
|
||||
- 验证:`cargo test -p api-server --manifest-path server-rs/Cargo.toml editor_reference`,并用前端 workflow 测试覆盖 `referenceImageSrcs` 进入图标生成请求;若快速编辑重开额外参考图,再补对应请求覆盖。
|
||||
- 关联:`server-rs/crates/api-server/src/editor_project.rs`、`server-rs/crates/spacetime-client/src/assets.rs`、`src/components/image-editor/useImageCanvasGenerationSubmissionWorkflow.ts`。
|
||||
|
||||
@@ -4012,7 +4012,7 @@
|
||||
## 画布 Agent 的规划请求不能关闭瞬时失败重试
|
||||
|
||||
- 现象:美术 Agent 对话返回红色错误气泡 `completion error: LLM 请求超时,累计尝试 1 次`;HTTP 本身仍返回 200,前端 20 分钟 transport timeout 没有触发。
|
||||
- 原因:规划请求虽然有 Agent 专用单次 timeout,但 `editor_agent_llm_client` 把 `max_retries` 硬编码为 0;VectorEngine `gpt-5.4-mini` 的偶发长尾、连接超时或可重试上游状态会在第一次失败后直接持久化成 system error。framework 的英文 `completion error` 前缀也被原样暴露给用户。
|
||||
- 原因:规划请求虽然有 Agent 专用单次 timeout,但 `vector_engine_llm_client` 把 `max_retries` 硬编码为 0;VectorEngine `gpt-5.4-mini` 的偶发长尾、连接超时或可重试上游状态会在第一次失败后直接持久化成 system error。framework 的英文 `completion error` 前缀也被原样暴露给用户。
|
||||
- 处理:120 秒改为前端软提示阈值:POST 仍 pending 时显示不入库的“仍在处理中,请耐心等待”;provider 明确断开/失败才写正式错误。专用 provider 单 attempt 使用 8 分钟 hard timeout,请求发起阶段读取 `GENARRATIVE_LLM_MAX_RETRIES`,但画布 Agent 最多重试 1 次且重试退避最多 60 秒。不要只计算单次 complete 的最坏时间:runner 还可因非法 JSON/工具校验失败进入后续轮次,必须从 handler 入口开始计算 18 分钟总 deadline,进入 `agent.prompt(...)` 时扣除会话锁/上下文准备已用时间,为持久化和前端 20 分钟 timeout 留出余量。响应头后的体读取/解析错误按明确失败收口,必须使用真实 attempt 计数;规划、配置和定价错误对用户统一为中文,原始诊断只记后端日志。重试发生在任何生成工具执行前,不会重复提交生成任务或扣费,不要通过提高前端 timeout 或 runner `max_turns` 掩盖 provider 重试缺失。
|
||||
- 验证:`platform-editor-agent` 测试锁定 8 分钟 hard timeout 与中文错误;前端 fake timer 用例锁定 120 秒前只显示思考动画、到点后显示耐心等待、成功/失败后移除;`platform-llm` 回归用例锁定第二次 attempt 成功响应头后的 body timeout 仍报累计 2 次;`api-server` 测试锁定专用 client retry、18 分钟整体 deadline 与中文直达错误。运行态排障按同一 request id 对齐 `platform_llm` failure stage 与 `/messages` 总耗时,并确认仍 pending 的请求不再在 120 秒形成错误气泡。
|
||||
- 关联:`server-rs/crates/platform-editor-agent/src/agent/agent.rs`、`server-rs/crates/platform-agent-harness/src/error.rs`、`server-rs/crates/api-server/src/state.rs`、`src/components/image-editor/EditorAgentConversation/useEditorAgentConversation.ts`、`src/components/image-editor/EditorAgentConversation/MessageBubble.tsx`、`src/services/image-editor/editorAgentClient.ts`。
|
||||
|
||||
Reference in New Issue
Block a user