4.8 KiB
4.8 KiB
| name | description |
|---|---|
| entity | 实体管理模块(W-03)——实体表(entity)CRUD、列表查询、实体文件导入(entity_import 记录),通过 load_entity() 挂载。 |
entity 模块
概述
实体管理模块,提供实体表(entity)增删改查与文件导入(entity_import 记录表)。依赖 world、scene 模块(逻辑关联,不加物理外键)。
数据模型
表 entity(models/entity.json)
| 字段 | 类型 | 说明 |
|---|---|---|
| id | str(32) | 主键 |
| world_id | str(32) | 所属世界(→world.id 逻辑关联) |
| scene_id | str(32) | 所属场景(→scene.id 逻辑关联,codes 段配置,不加物理外键) |
| name | str(255) | 实体名称 |
| code | str(64) | 实体编码(唯一,idx_entity_code) |
| entity_type | str(16) | 实体类型(appcodes entity_type) |
| status | str(16) | 状态(appcodes entity_status) |
| attributes_json | text | 属性 JSON |
| created_at | timestamp | 创建时间 |
| updated_at | timestamp | 更新时间 |
- 主键
["id"];唯一索引idx_entity_code(code);索引idx_entity_world(world_id)、idx_entity_scene(scene_id) - codes:world_id → world(id/name)、scene_id → scene(id/name)、entity_type → appcodes_kv(parentid='entity_type')、status → appcodes_kv(parentid='entity_status')
表 entity_import(models/entity_import.json,只读)
| 字段 | 类型 | 说明 |
|---|---|---|
| id | str(32) | 主键 |
| world_id | str(32) | 目标世界 |
| scene_id | str(32) | 目标场景 |
| file_name | str(255) | 导入文件名 |
| total / success / fail | int | 总数 / 成功 / 失败(默认 0) |
| status | str(16) | 导入状态(appcodes import_status:0 进行中/1 成功/2 失败) |
| created_at | timestamp | 导入时间 |
- 主键
["id"];索引idx_entity_import_world(world_id);只读记录,不可手工增删改
关键接口(load_entity() 挂载到 ServerEnv)
list_entities(params)→{list, total}(sqlPaging 分页,支持 world_id/scene_id/entity_type/status/name/code 过滤 + sort/order)get_entity({id})→{data}或错误create_entity(ns)→ 校验 + world/scene 存在校验 + 自动 id/created_at/updated_at;返回{success, id}update_entity(ns)→ 写 updated_at、剔除_text后缀、world/scene 校验delete_entity({id})→{success, id}import_entities({world_id, scene_id, file_name, rows})→{success, total, success_count, fail, file_name}(事务批量:先全量解析+校验(含文件内编码查重),再逐条插入;任一条失败整批回滚,无脏数据;success_count 避免与布尔 success 冲突)parse_entity_file(content, filename)→{rows: [...]}(JSON 数组 / JSON Lines / CSV 表头)get_world_options()/get_scene_options()/get_entity_type_options()/get_entity_status_options()/get_import_status_options()→[{value, text}]
wwwroot/api/.dspy(REST 统一前缀 /api/,宿主挂载后为 /entity/api/*.dspy)
entity_list.dspy(分页{list,total})、entity_get.dspy、entity_create.dspy、entity_update.dspy、entity_delete.dspyentity_import.dspy(world_id + file → parse_entity_file → import_entities)get_search_world_id.dspy/get_search_scene_id.dspy/get_search_entity_type.dspy/get_search_status.dspy/get_search_import_status.dspy(字典下拉)
错误结构(统一)
{code, message, field, detail};code:PARAM_REQUIRED / FIELD_REQUIRED / FIELD_TOO_LONG /
WORLD_NOT_FOUND / SCENE_NOT_FOUND / DUPLICATE_CODE / PARSE_ERROR / INVALID_JSON / DB_ERROR / NOT_FOUND。
非法输入 100% 拦截不落库。
陷阱
- 库名禁止硬编码:.py 用
ServerEnv().get_module_dbname("entity"),.dspy 用get_module_dbname("entity")(全局);world/scene 表分别在 world/scene 模块库(get_module_dbname("world"/"scene")),appcodes 在get_module_dbname("appbase") - dspy 无 import(json/get_sor_context/debug/params_kw 均预加载全局);函数经 load_entity() 注册后为全局,直接调用
create_entity/import_entities必须显式设置created_at = curDateString(),否则 sor.C 静默丢记录entity_import记录 total/success/fail 必须为 intimport_entities返回用success_count(避免与布尔success键冲突)- 三处同步注册:entity/init.py 导出 ← entity/init.py 实现 ← load_entity() 注册(含复数别名 create_entities/update_entities/delete_entities)
- 返回
{list,total}分页用sor.sqlPaging,不要硬编码 LIMIT/OFFSET - CRUD json
new_data_url指向自定义api/entity_create.dspy;entity_import 为只读列表,无 editable
依赖
- world(world_id 逻辑关联 + 世界下拉)、scene(scene_id 逻辑关联 + 场景下拉)、appbase(appcodes 字典)、rbac(权限)