mirror of
https://github.com/ThearchyHelios/AgentLab.git
synced 2026-11-15 03:51:58 +00:00
277982ead3
- 蓝图:bp_* 操作和逐卡白名单、蓝图检查、留痕、按蓝图判权限;五个场景模板加自由形(骨架、关节、应用骨架、定时任务),实例化与骨架比对;BlueprintApplier / TemplateApplier(只收模板声明过的关节)与自查;look 新类别口径卡;蓝图对话和填关节两个流式接口,不同组的关节并行填、出错的组串行重试;模板列表 - 试运行与发布单:四种起点(对话、模板、问数据的一轮、已发布版本);试运行是探索运行,草稿应用按这次运行解析、印章写试运行,流程类派给自己、不触发升级;发布单九步、预检只读、每步留痕、停下后接着做、核对卡片指纹和应用管理权、启动时整理中断的单;白话层覆盖全部问题编号 - 记录表与文件:平台托管只追加的记录表、按高水位固定数据、连接上的临时视图做行级可见、写入走动作(records_append)、表版本在发布时切换、草稿不影响线上、记录列表遮敏感列;文件按哈希存、两步上传、提交时绑定运行、下载按读权限、清理、file_text、按配方导入一期(table_import_period) - 个人应用:存成个人应用(问数据的约束)、刷新(遮罩、只读、每日上限)、只有拥有者看得见、提交审核与共享副本、开关下发到认人接口;页面编辑的候选;隐藏组件不下发;三条新检查
127 lines
9.1 KiB
Python
127 lines
9.1 KiB
Python
"""受信组件目录 v1(docs/design/app-platform-and-look.md §2.2、§3.5)。
|
||
|
||
一份目录,四个使用方:应用页、人工节点表单、agent 拟的询问、助手生成。模型只能从这里挑组件;前端只有一张
|
||
「名字 → 渲染器」的表,遇到不认识的组件显示「此组件需要更新前端」,不报错、不空白。
|
||
|
||
每个组件登记:名字、中文名、类别、版本、props 的 JSON Schema、允许的绑定种类、能不能有子组件。
|
||
props 里每一项都写 title(属性面板上的中文名),取值不直观的另写 description;枚举写 x-enum-labels(和 enum 按位置
|
||
对应,同表单 agentlab.form/1 的写法);给人看的文字(标题、名称、说明)标 x-text,应用页上直接改的「改文字」只改这几项,
|
||
列名、换算这类写给解析器的字符串不标。这几样是注解,不参与校验。
|
||
服务端校验器和解析器由 app/apps/ 的实现按名字注册(BE-3);开发者扩展组件时,目录项、校验器、解析器、前端渲染器
|
||
四样都要给,缺一样启动即报错(check_registry)。
|
||
"""
|
||
from __future__ import annotations
|
||
|
||
from typing import Any
|
||
|
||
CATEGORIES = ("layout", "display", "input", "process")
|
||
CATEGORY_LABEL = {"layout": "布局", "display": "展示", "input": "输入", "process": "流程"}
|
||
|
||
|
||
def _props(**properties: Any) -> dict[str, Any]:
|
||
return {"type": "object", "additionalProperties": False, "properties": properties}
|
||
|
||
|
||
def _text(title: str, **more: Any) -> dict[str, Any]:
|
||
"""给人看的一行字(标题、名称、单位):x-text 标出来,页面上直接改的「改文字」改它(normal-user-apps N6)。"""
|
||
return {"type": "string", "maxLength": 200, "title": title, "x-text": True, **more}
|
||
|
||
|
||
def _long(title: str) -> dict[str, Any]:
|
||
return {"type": "string", "maxLength": 4000, "title": title, "x-text": True}
|
||
|
||
|
||
def _code(title: str, **more: Any) -> dict[str, Any]:
|
||
"""写给解析器的短字符串(列名、换算):不是给人看的文字,「改文字」不碰。"""
|
||
return {"type": "string", "maxLength": 200, "title": title, **more}
|
||
|
||
|
||
def _enum(title: str, **labels: str) -> dict[str, Any]:
|
||
"""枚举:值是键,中文是 x-enum-labels(按位置对应)。"""
|
||
return {"enum": list(labels), "x-enum-labels": list(labels.values()), "title": title}
|
||
|
||
|
||
_CHART = _enum("图形", line="折线图", bar="柱状图")
|
||
|
||
COMPONENTS: list[dict[str, Any]] = [
|
||
# ---- 布局 ----
|
||
{"name": "page", "label": "页面", "category": "layout", "version": 1, "children": True, "bindings": [],
|
||
"props": _props(title=_text("标题"))},
|
||
{"name": "section", "label": "分区", "category": "layout", "version": 1, "children": True, "bindings": [],
|
||
"props": _props(title=_text("标题"), description=_long("说明"))},
|
||
{"name": "columns", "label": "分栏", "category": "layout", "version": 1, "children": True, "bindings": [],
|
||
"props": _props(count={"type": "integer", "minimum": 1, "maximum": 4, "title": "列数"})},
|
||
{"name": "tabs", "label": "页签", "category": "layout", "version": 1, "children": True, "bindings": [],
|
||
"props": _props(labels={"type": "array", "items": {"type": "string", "maxLength": 200}, "maxItems": 8,
|
||
"title": "页签名", "description": "按顺序对应里面的子组件"})},
|
||
{"name": "divider", "label": "分隔线", "category": "layout", "version": 1, "children": False, "bindings": [],
|
||
"props": _props()},
|
||
# ---- 展示 ----
|
||
{"name": "stamp", "label": "印章", "category": "display", "version": 1, "children": False,
|
||
"bindings": ["run"], "props": _props(compact={"type": "boolean", "title": "紧凑显示"})},
|
||
{"name": "metric", "label": "指标块", "category": "display", "version": 1, "children": False,
|
||
"bindings": ["metric", "cell"],
|
||
"props": _props(label=_text("名称"),
|
||
unit=_text("单位", description="绑定单元格时写在数下面;绑定指标时数里已经带着口径卡的单位"),
|
||
conv=_code("换算", description="万、亿、pct(百分比)、int(取整)或 .N(保留 N 位小数)"))},
|
||
{"name": "series", "label": "趋势", "category": "display", "version": 1, "children": False,
|
||
"bindings": ["series"], "props": _props(label=_text("名称"), chart=_CHART)},
|
||
{"name": "table", "label": "表格", "category": "display", "version": 1, "children": False,
|
||
"bindings": ["query"],
|
||
"props": _props(title=_text("标题"),
|
||
columns={"type": "array", "items": {"type": "string", "maxLength": 200}, "title": "显示的列",
|
||
"description": "列名,不填显示全部列"},
|
||
sort={"type": "string", "title": "排序列", "description": "按哪一列排序,写列名;前面加「-」为降序"},
|
||
limit={"type": "integer", "minimum": 1, "title": "最多显示行数"})},
|
||
{"name": "chart", "label": "图表", "category": "display", "version": 1, "children": False,
|
||
"bindings": ["query"],
|
||
"props": _props(title=_text("标题"), chart=_CHART, x=_code("横轴列"),
|
||
y={"type": "array", "items": {"type": "string", "maxLength": 200}, "maxItems": 4,
|
||
"title": "纵轴列", "description": "最多 4 列"})},
|
||
{"name": "report", "label": "报告", "category": "display", "version": 1, "children": False,
|
||
"bindings": ["report"], "props": _props(title=_text("标题"))},
|
||
{"name": "text", "label": "文字", "category": "display", "version": 1, "children": False, "bindings": [],
|
||
"props": _props(markdown=_long("正文(Markdown)"))},
|
||
{"name": "notice", "label": "提示", "category": "display", "version": 1, "children": False, "bindings": [],
|
||
"props": _props(text=_long("提示文字"), tone=_enum("样式", info="说明", warn="提醒", error="错误"))},
|
||
{"name": "field", "label": "字段", "category": "display", "version": 1, "children": False,
|
||
"bindings": ["input", "output", "run"], "props": _props(label=_text("名称"))},
|
||
{"name": "status", "label": "状态", "category": "display", "version": 1, "children": False,
|
||
"bindings": ["run"], "props": _props(label=_text("名称"))},
|
||
# ---- 输入 ----
|
||
{"name": "form", "label": "表单", "category": "input", "version": 1, "children": False, "bindings": [],
|
||
"props": _props(form={"type": "string", "title": "表单"}, submit_label=_text("提交按钮文字"))},
|
||
# ---- 流程 ----
|
||
{"name": "entry_button", "label": "发起按钮", "category": "process", "version": 1, "children": False,
|
||
"bindings": [], "props": _props(entry={"type": "string", "title": "入口"}, label=_text("按钮文字"))},
|
||
{"name": "instance_list", "label": "实例列表", "category": "process", "version": 1, "children": False,
|
||
"bindings": [], "props": _props(entry={"type": "string", "title": "入口"},
|
||
who=_enum("显示谁的", mine="我发起的", all="全部实例"),
|
||
limit={"type": "integer", "minimum": 1, "maximum": 200, "title": "最多显示几条"})},
|
||
{"name": "instance_header", "label": "实例概况", "category": "process", "version": 1, "children": False,
|
||
"bindings": [], "props": _props()},
|
||
{"name": "instance_timeline", "label": "实例进度", "category": "process", "version": 1, "children": False,
|
||
"bindings": [], "props": _props()},
|
||
{"name": "task_list", "label": "待办列表", "category": "process", "version": 1, "children": False,
|
||
"bindings": [], "props": _props(scope=_enum("范围", mine="派给我的", instance="本实例的"))},
|
||
{"name": "task_form", "label": "待办表单", "category": "process", "version": 1, "children": False,
|
||
"bindings": ["task"], "props": _props()},
|
||
{"name": "signoffs", "label": "会签进度", "category": "process", "version": 1, "children": False,
|
||
"bindings": ["task"], "props": _props()},
|
||
{"name": "action_status", "label": "动作状态", "category": "process", "version": 1, "children": False,
|
||
"bindings": ["action"], "props": _props(label=_text("名称"))},
|
||
# 记录表的逐行(docs/design/normal-user-apps.md N8):每次打开按看的人实时过滤(use 只看自己提交的),不走封存
|
||
{"name": "records_list", "label": "记录列表", "category": "process", "version": 1, "children": False,
|
||
"bindings": [], "props": _props(title=_text("标题"),
|
||
table=_code("记录表", description="不填就是这个应用的第一张记录表"),
|
||
who=_enum("显示谁的", mine="我提交的", all="全部(要有查看全部的权限)"),
|
||
limit={"type": "integer", "minimum": 1, "maximum": 200, "title": "最多显示几条"})},
|
||
]
|
||
|
||
BY_NAME: dict[str, dict[str, Any]] = {c["name"]: c for c in COMPONENTS}
|
||
|
||
|
||
def catalog_payload() -> dict[str, Any]:
|
||
"""GET /api/apps/catalog 的返回:组件目录 + 类别名。助手生成时也给模型看这一份(只给名字、中文名、props、绑定)。"""
|
||
return {"version": 1, "categories": CATEGORY_LABEL, "components": COMPONENTS}
|