Files
Uni-Lab-OS/.cursor/skills/virtual-workbench/SKILL.md
2026-04-13 17:02:38 +08:00

10 KiB
Raw Blame History

name, description
name description
virtual-workbench Operate Virtual Workbench via REST API — prepare materials, move to heating stations, start heating, move to output, transfer resources. Use when the user mentions virtual workbench, virtual_workbench, 虚拟工作台, heating stations, material processing, or workbench operations.

Virtual Workbench API Skill

设备信息

  • device_id: virtual_workbench
  • Python 源码: unilabos/devices/virtual/workbench.py
  • 设备类: VirtualWorkbench
  • 动作数: 6auto-prepare_materials, auto-move_to_heating_station, auto-start_heating, auto-move_to_output, transfer, manual_confirm
  • 设备描述: 模拟工作台,包含 1 个机械臂(每次操作 2s独占锁和 3 个加热台(每次加热 60s可并行

典型工作流程

  1. prepare_materials — 生成 A1-A5 物料5 个 output handle
  2. move_to_heating_station — 物料并发竞争机械臂,移动到空闲加热台
  3. start_heating — 启动加热3 个加热台可并行)
  4. move_to_output — 加热完成后移到输出位置 Cn

前置条件(缺一不可)

使用本 skill 前,必须先确认以下信息。如果缺少任何一项,立即向用户询问并终止,等补齐后再继续。

1. ak / sk → AUTH

从启动参数 --ak --sk 或 config.py 中获取,生成 tokenbase64(ak:sk)Authorization: Lab <token>

2. --addr → BASE URL

--addr BASE
test https://leap-lab.test.bohrium.com
uat https://leap-lab.uat.bohrium.com
local http://127.0.0.1:48197
不传(默认) https://leap-lab.bohrium.com

确认后设置:

BASE="<根据 addr 确定的 URL>"
AUTH="Authorization: Lab <token>"

两项全部就绪后才可发起 API 请求。

Session State

  • lab_uuid — 实验室 UUID首次通过 API #1 自动获取,不需要问用户
  • device_namevirtual_workbench

请求约定

所有请求使用 curl -sPOST/PATCH/DELETE 需加 Content-Type: application/json

Windows 平台必须使用 curl.exe(而非 PowerShell 的 curl 别名)。


API Endpoints

1. 获取实验室信息(自动获取 lab_uuid

curl -s -X GET "$BASE/api/v1/edge/lab/info" -H "$AUTH"

返回 data.uuidlab_uuiddata.namelab_name

2. 创建工作流

curl -s -X POST "$BASE/api/v1/lab/workflow/owner" \
  -H "$AUTH" -H "Content-Type: application/json" \
  -d '{"name":"<名称>","lab_uuid":"<lab_uuid>","description":"<描述>"}'

返回 data.uuidworkflow_uuid。创建成功后告知用户链接:$BASE/laboratory/$lab_uuid/workflow/$workflow_uuid

3. 创建节点

curl -s -X POST "$BASE/api/v1/edge/workflow/node" \
  -H "$AUTH" -H "Content-Type: application/json" \
  -d '{"workflow_uuid":"<workflow_uuid>","resource_template_name":"virtual_workbench","node_template_name":"<action_name>"}'
  • resource_template_name 固定为 virtual_workbench
  • node_template_name — action 名称(如 auto-prepare_materials, auto-move_to_heating_station

4. 删除节点

curl -s -X DELETE "$BASE/api/v1/lab/workflow/nodes" \
  -H "$AUTH" -H "Content-Type: application/json" \
  -d '{"node_uuids":["<uuid1>"],"workflow_uuid":"<workflow_uuid>"}'

5. 更新节点参数

curl -s -X PATCH "$BASE/api/v1/lab/workflow/node" \
  -H "$AUTH" -H "Content-Type: application/json" \
  -d '{"workflow_uuid":"<wf_uuid>","uuid":"<node_uuid>","param":{...}}'

参考 action-index.md 确定哪些字段是 Slot。

6. 查询节点 handles

curl -s -X POST "$BASE/api/v1/lab/workflow/node-handles" \
  -H "$AUTH" -H "Content-Type: application/json" \
  -d '{"node_uuids":["<node_uuid_1>","<node_uuid_2>"]}'

7. 批量创建边

curl -s -X POST "$BASE/api/v1/lab/workflow/edges" \
  -H "$AUTH" -H "Content-Type: application/json" \
  -d '{"edges":[{"source_node_uuid":"<uuid>","target_node_uuid":"<uuid>","source_handle_uuid":"<uuid>","target_handle_uuid":"<uuid>"}]}'

8. 启动工作流

curl -s -X POST "$BASE/api/v1/lab/workflow/<workflow_uuid>/run" -H "$AUTH"

9. 运行设备单动作

curl -s -X POST "$BASE/api/v1/lab/mcp/run/action" \
  -H "$AUTH" -H "Content-Type: application/json" \
  -d '{"lab_uuid":"<lab_uuid>","device_id":"virtual_workbench","action":"<action_name>","action_type":"<type>","param":{...}}'

param 直接放 goal 里的属性,不要再包一层 {"goal": {...}}

WARNING: action_type 必须正确,传错会导致任务永远卡住无法完成。 从下表或 actions/<name>.jsontype 字段获取。

action_type 速查表

action action_type
auto-prepare_materials UniLabJsonCommand
auto-move_to_heating_station UniLabJsonCommand
auto-start_heating UniLabJsonCommand
auto-move_to_output UniLabJsonCommand
transfer UniLabJsonCommandAsync
manual_confirm UniLabJsonCommand

10. 查询任务状态

curl -s -X GET "$BASE/api/v1/lab/mcp/task/<task_uuid>" -H "$AUTH"

11. 运行工作流单节点

curl -s -X POST "$BASE/api/v1/lab/mcp/run/workflow/action" \
  -H "$AUTH" -H "Content-Type: application/json" \
  -d '{"node_uuid":"<node_uuid>"}'

12. 获取资源树(物料信息)

curl -s -X GET "$BASE/api/v1/lab/material/download/$lab_uuid" -H "$AUTH"

注意 lab_uuid 在路径中。返回 data.nodes[] 含所有节点(设备 + 物料),每个节点含 nameuuidtypeparent

13. 获取工作流模板详情

curl -s -X GET "$BASE/api/v1/lab/workflow/template/detail/$workflow_uuid" -H "$AUTH"

必须使用 /lab/workflow/template/detail/{uuid},其他路径会返回 404。

14. 按名称查询物料模板

curl -s -X GET "$BASE/api/v1/lab/material/template/by-name?lab_uuid=$lab_uuid&name=<template_name>" -H "$AUTH"

返回 data.uuidres_template_uuid,用于 API #15。

15. 创建物料节点

curl -s -X POST "$BASE/api/v1/edge/material/node" \
  -H "$AUTH" -H "Content-Type: application/json" \
  -d '{"res_template_uuid":"<uuid>","name":"<名称>","display_name":"<显示名>","parent_uuid":"<父节点uuid>","data":{...}}'

16. 更新物料节点

curl -s -X PUT "$BASE/api/v1/edge/material/node" \
  -H "$AUTH" -H "Content-Type: application/json" \
  -d '{"uuid":"<节点uuid>","display_name":"<新名称>","data":{...}}'

Placeholder Slot 填写规则

placeholder_keys Slot 类型 填写格式 选取范围
unilabos_resources ResourceSlot {"id": "/path/name", "name": "name", "uuid": "xxx"} 仅物料节点(非设备)
unilabos_devices DeviceSlot "/parent/device_name" 仅设备节点type=device
unilabos_nodes NodeSlot "/parent/node_name" 所有节点(设备 + 物料)
unilabos_class ClassSlot "class_name" 注册表中已注册的资源类

virtual_workbench 设备的 Slot 字段表

Action 字段 Slot 类型 说明
transfer resource ResourceSlot 待转移物料数组
transfer target_device DeviceSlot 目标设备路径
transfer mount_resource ResourceSlot 目标孔位数组
manual_confirm resource ResourceSlot 确认用物料数组
manual_confirm target_device DeviceSlot 确认用目标设备
manual_confirm mount_resource ResourceSlot 确认用目标孔位数组

prepare_materialsmove_to_heating_stationstart_heatingmove_to_output 这 4 个动作无 Slot 字段,参数为纯数值/整数。


渐进加载策略

  1. SKILL.md(本文件)— API 端点 + session state 管理 + 设备工作流概览
  2. action-index.md — 按分类浏览 6 个动作的描述和核心参数
  3. actions/<name>.json — 仅在需要构建具体请求时,加载对应 action 的完整 JSON Schema

完整工作流 Checklist

Task Progress:
- [ ] Step 1: GET /edge/lab/info 获取 lab_uuid
- [ ] Step 2: 获取资源树 (GET #12) → 记住可用物料
- [ ] Step 3: 读 action-index.md 确定要用的 action 名
- [ ] Step 4: 创建工作流 (POST #2) → 记住 workflow_uuid告知用户链接
- [ ] Step 5: 创建节点 (POST #3, resource_template_name=virtual_workbench) → 记住 node_uuid + data.param
- [ ] Step 6: 根据 _unilabos_placeholder_info 和资源树,填写 data.param 中的 Slot 字段
- [ ] Step 7: 更新节点参数 (PATCH #5)
- [ ] Step 8: 查询节点 handles (POST #6) → 获取各节点的 handle_uuid
- [ ] Step 9: 批量创建边 (POST #7) → 用 handle_uuid 连接节点
- [ ] Step 10: 启动工作流 (POST #8) 或运行单节点 (POST #11)
- [ ] Step 11: 查询任务状态 (GET #10) 确认完成

典型 5 物料并发加热工作流示例

prepare_materials (count=5)
  ├─ channel_1 → move_to_heating_station (material_number=1) → start_heating → move_to_output
  ├─ channel_2 → move_to_heating_station (material_number=2) → start_heating → move_to_output
  ├─ channel_3 → move_to_heating_station (material_number=3) → start_heating → move_to_output
  ├─ channel_4 → move_to_heating_station (material_number=4) → start_heating → move_to_output
  └─ channel_5 → move_to_heating_station (material_number=5) → start_heating → move_to_output

创建节点时,prepare_materials 的 5 个 output handlechannel_1 ~ channel_5)分别连接到 5 个 move_to_heating_station 节点的 material_input handle。每个 move_to_heating_stationheating_station_outputmaterial_number_output 连接到对应 start_heatingstation_id_inputmaterial_number_input