Files
DronePlanning/backend_service/history/20260120_115816_plan.json
2026-02-20 23:04:09 +08:00

78 lines
20 KiB
JSON
Raw Permalink Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
{
"timestamp": "2026-01-20T11:58:16.067601",
"request": "无人机当前在空中往广场西边飞200米持续监控5分钟发现人就拍照告诉我到时间可以返航。",
"response": {
"root": {
"type": "Sequence",
"name": "MainTask",
"children": [
{
"type": "action",
"name": "fly_to_waypoint",
"params": {
"x": -217.0,
"y": 360.0,
"z": 3.0
}
},
{
"type": "Parallel",
"name": "MonitorAndPhoto",
"params": {
"policy": "success_on_one"
},
"children": [
{
"type": "action",
"name": "loiter",
"params": {
"duration": 300
}
},
{
"type": "decorator",
"name": "SuccessIsFailure",
"child": {
"type": "Sequence",
"name": "CheckAndPhoto",
"children": [
{
"type": "action",
"name": "object_detect",
"params": {
"target_class": "person"
}
},
{
"type": "condition",
"name": "object_detected",
"params": {
"target_class": "person"
}
},
{
"type": "action",
"name": "take_photos",
"params": {
"target_class": "person"
}
}
]
}
}
]
},
{
"type": "action",
"name": "return_emergency",
"params": {
"reason": "返航"
}
}
]
},
"plan_id": "44db1903-84e2-4fd3-904e-8e12a33cd06d",
"visualization_url": "/static/py_tree.png",
"final_prompt": "=== System Prompt ===\n任务根据用户任意任务指令生成结构化可执行的无人机行为树PytreeJSON。**仅输出单一JSON对象无任何自然语言、注释或额外内容**。\n\n## 一、核心节点定义(格式不可修改,确保后端解析)\n#### 1. 可用节点定义 (必须遵守)\n你必须严格从以下JSON定义的列表中选择节点构建行为树不允许使用未定义节点\n```json\n{\n \"actions\": [\n {\"name\":\"takeoff\",\"params\":{\"altitude\":\"float[1,100]默认2\"}},\n {\"name\":\"land\",\"params\":{\"mode\":\"'current'/'home'\"}},\n {\"name\":\"fly_to_waypoint\",\"params\":{\"x\":\"±10000\",\"y\":\"±10000\",\"z\":\"[1,5000]\",\"acceptance_radius\":\"默认2.0\",\"desc\":\"仅当指令提及具体地点(如'去广场'、'去大门')或需计算明确坐标时使用\"}},\n {\"name\":\"fly_sequence\",\"params\":{\"waypoints\":\"list[dict] (e.g. [{'x':10,'y':20,'z':5}, ...])\",\"coordinate_frame\":\"'global'/'local_enu'global:经纬度, local_enu:以起飞点为原点的东南天坐标系)\",\"speed\":\"float,可选\"}},\n {\"name\":\"move_direction\",\"params\":{\"direction\":\"north/south/east/west/forward/backward/left/right\",\"distance\":\"[1,10000],缺省则持续移动\",\"speed\":\"float,可选\",\"desc\":\"当指令仅包含'往东/西...飞xx米'且无具体地点名词时,必须使用此节点\"}},\n {\"name\":\"approach_target\",\"params\":{\"target_class\":\"string,要趋近的目标类别\",\"description\":\"string,可选,目标属性描述\",\"stop_distance\":\"float,期望的最终停止距离\",\"speed\":\"float,可选,期望的逼近速度\"}},\n {\"name\":\"rotate\",\"params\":{\"angle\":\"float,无人机自身旋转角度(正数逆时针,负数顺时针)\",\"angular_velocity\":\"rad/s,旋转角速度\"}},\n {\"name\":\"rotate_search\",\"params\":{\"target_class\":\"同object_detect\",\"description\":\"string,可选,目标属性描述\",\"step_angle\":\"float,可选,每一步旋转的角度\",\"total_rotation\":\"float,可选,总共旋转搜索的角度\"}},\n {\"name\":\"manual_confirmation\",\"params\":{}},\n {\"name\":\"loiter\",\"params\":{\"duration\":\"[1,600]秒/until_condition:可选\"}},\n {\"name\":\"object_detect\",\"params\":{\"target_class\":\"person,bicycle,car,motorcycle,airplane,bus,train,truck,boat,traffic_light,fire_hydrant,stop_sign,parking_meter,bench,bird,cat,dog,horse,sheep,cow,elephant,bear,zebra,giraffe,backpack,umbrella,handbag,tie,suitcase,frisbee,skis,snowboard,sports_ball,kite,baseball_bat,baseball_glove,skateboard,surfboard,tennis_racket,bottle,wine_glass,cup,fork,knife,spoon,bowl,banana,apple,sandwich,orange,broccoli,carrot,hot_dog,pizza,donut,cake,chair,couch,potted_plant,bed,dining_table,toilet,tv,laptop,mouse,remote,keyboard,cell_phone,microwave,oven,toaster,sink,refrigerator,book,clock,vase,scissors,teddy_bear,hair_drier,toothbrush,garbage\",\"description\":\"可选,\",\"count\":\"默认1\"}},\n {\"name\":\"search_pattern\",\"params\":{\"pattern_type\":\"spiral/grid\",\"center_x\":\"±10000\",\"center_y\":\"±10000\",\"center_z\":\"[1,5000]\",\"radius\":\"[5,1000]\",\"target_class\":\"同object_detect\",\"description\":\"可选,目标属性\",\"count\":\"默认1\"}},\n {\"name\":\"track_object\",\"params\":{\"target_class\":\"同object_detect\",\"description\":\"可选,目标属性\",\"track_time\":\"[1,600]秒(必传,不可用'duration'\",\"min_confidence\":\"[0.5,1.0]默认0.7\",\"safe_distance\":\"[2,50]默认10\"}},\n {\"name\":\"deliver_payload\",\"params\":{\"payload_type\":\"string\",\"release_altitude\":\"[2,100]默认5\"}},\n {\"name\":\"system_checks\",\"params\":{\"check_level\":\"basic/comprehensive只能在起飞takeoff节点前使用空中无需使用该节点\"}},\n {\"name\":\"return_emergency\",\"params\":{\"reason\":\"string此节点仅用于【无明确目的地】的立即返航默认回起飞点。若指令包含“回到xx地”、“去xx地”即使包含“紧急”二字**严禁**使用此节点必须使用fly_to_waypoint\"}},\n {\"name\":\"take_photos\",\"params\":{\"target_class\":\"同object_detect\",\"description\":\"可选,目标属性\",\"track_time\":\"[1,600]秒(必传,不可用'duration'\",\"min_confidence\":\"[0.5,1.0]默认0.7\",\"safe_distance\":\"[2,50]默认10\"}}\n ],\n \"conditions\": [\n {\"name\":\"at_waypoint\",\"params\":{\"x\":\"±10000\",\"y\":\"±10000\",\"z\":\"[1,5000]\",\"tolerance\":\"默认3.0\"}},\n {\"name\":\"object_detected\",\"params\":{\"target_class\":\"同object_detect必传\",\"description\":\"可选,目标属性\",\"count\":\"默认1\"}}\n ],\n \"control_flow\": [\n {\"name\":\"Sequence\",\"params\":{},\"children\":\"子节点数组(按序执行,全成功则成功)\"},\n {\"name\":\"Selector\",\"params\":{\"memory\":\"默认true\"},\"children\":\"子节点数组(执行到成功为止)\"},\n {\"name\":\"Parallel\",\"params\":{\"policy\":\"all_success/success_on_one\"},\"children\":\"子节点数组同时执行默认all_success\"}\n ],\n \"decorators\": [\n {\"name\":\"SuccessIsFailure\",\"params\":{},\"child\":\"单一子节点(将子节点的成功结果反转为失败)\"}\n ]\n}\n```\n\n\n## 二、节点必填字段后端Schema强制要求缺一验证失败\n每个节点必须包含以下字段字段名/类型不可自定义:\n1. **`type`** \n - 动作节点→`\"action\"`,条件节点→`\"condition\"`,控制流节点→`\"Sequence\"`/`\"Selector\"`/`\"Parallel\"`,装饰器节点→`\"decorator\"`\n2. **`name`**必须是上述JSON中定义的`name`值;\n3. **`params`**:严格匹配上述节点的`params`定义,无自定义参数;\n4. **`children`**:仅控制流节点必含(子节点数组);\n5. **`child`**:仅装饰器节点必含(单一子节点对象,非数组)。\n\n\n## 三、标准任务结构模板(单次起降流程)\n当无人机在地面时大多数任务应遵循“起飞 -> 移动 -> 条件判断 -> 执行 -> 返航/降落”的单次闭环流程,参考结构如下:\n```json\n{\n \"root\": {\n \"type\": \"Sequence\",\n \"name\": \"MainTask\",\n \"children\": [\n {\"type\":\"action\",\"name\":\"system_checks\",\"params\":{\"check_level\":\"comprehensive\"}},\n {\"type\":\"action\",\"name\":\"takeoff\",\"params\":{\"altitude\":10.0}},\n {\"type\":\"action\",\"name\":\"fly_to_waypoint\",\"params\":{\"x\":100.0,\"y\":50.0,\"z\":10.0}}, // 接近目标区域\n // --- 核心任务区 (根据指令替换) ---\n // --- 任务1执行---\n {\"type\":\"action\",\"name\":\"rotate_search\",\"params\":{\"target_class\":\"person\",\"description\":\"目标描述\"}},\n {\"type\":\"action\",\"name\":\"object_detect\",\"params\":{\"target_class\":\"person\",\"description\":\"目标描述\"}},\n // ----条件判断(根据指令替换) -----\n {\"type\":\"condition\",\"name\":\"object_detected\",\"params\":{\"target_class\":\"person\",\"description\":\"扎辫子女子\"}},\n // --- 任务2执行---\n {\"type\":\"action\",\"name\":\"take_photos\",\"params\":{\"target_class\":\"person\",\"description\":\"扎辫子女子\"}}, \n // 默认不需要降落节点,除非用户明确要求\n ]\n }\n}\n```\n\n## 四、场景示例(请灵活参考)\n\n#### 场景 1线性搜索任务Sequence + Selector\n**指令**:“无人机当前在地面,去研究所正大门,搜索扎辫子女子,找到后拍照。”\n**思路**无人机在地面则需要先自检然后起飞获取研究所正大门坐标调用fly_to_waypoint节点到达该地然后调用rotate_search节点搜索目标女子再使用object_detected条件节点这样就可以作为take_photos节点的依据。\n**结构**Sequence (按顺序执行)\n```json\n{\n \"root\": {\n \"type\": \"Sequence\",\n \"name\": \"MainSearchTask\",\n \"children\": [\n {\"type\":\"action\",\"name\":\"takeoff\",\"params\":{\"altitude\":10.0}},\n {\"type\":\"action\",\"name\":\"fly_to_waypoint\",\"params\":{\"x\":100.0,\"y\":50.0,\"z\":10.0}}, \n {\"type\":\"action\",\"name\":\"rotate_search\",\"params\":{\"target_class\":\"person\",\"description\":\"扎辫子女子\"}},\n {\n \"type\": \"Selector\",\n \"name\": \"CheckAndPhoto\",\n \"children\": [\n {\n \"type\": \"Sequence\",\n \"name\": \"PhotoIfFound\",\n \"children\": [\n {\"type\":\"condition\",\"name\":\"object_detected\",\"params\":{\"target_class\":\"person\",\"description\":\"扎辫子女子\"}},\n {\"type\":\"action\",\"name\":\"take_photos\",\"params\":{\"target_class\":\"person\",\"description\":\"扎辫子女子\",\"track_time\":10.0}}\n ]\n },\n {\"type\":\"action\",\"name\":\"loiter\",\"params\":{\"duration\":5.0}} // 未发现时的备选动作\n ]\n }\n ]\n }\n}\n```\n\n#### 场景 2带中断逻辑的巡逻Selector 示例)\n**指令**“无人机当前在地面飞往航点A。如果途中发现可疑人员则悬停。”\n**参考知识**航点A的坐标x:100.0,y:50.0\n**思路**无人机在地面则需要先自检然后起飞获取航点A的坐标调用fly_to_waypoint节点到达该地但同时需要注意看到可疑人员需要悬停意味着一边进行识别识别到进行悬停因此要在object_detect节点后有一个object_detected条件节点作为悬停的条件。\n**结构**\n```json\n{\n \"root\": {\n \"type\": \"Sequence\",\n \"children\": [\n {\"type\":\"action\",\"name\":\"system_checks\",\"params\":{\"check_level\":\"basic\"}},\n {\"type\":\"action\",\"name\":\"takeoff\",\"params\":{\"altitude\":10.0}},\n {\n \"type\": \"Selector\",\n \"name\": \"FlyOrDetect\",\n \"children\": [\n {\n \"type\": \"Sequence\", \n \"name\": \"InterruptionLogic\",\n \"children\": [\n {\"type\":\"action\",\"name\":\"object_detect\",\"params\":{\"target_class\":\"person\"}},\n {\"type\":\"condition\",\"name\":\"object_detected\",\"params\":{\"target_class\":\"person\"}},\n {\"type\":\"action\",\"name\":\"loiter\",\"params\":{\"duration\":5.0}}\n ]\n },\n {\"type\":\"action\",\"name\":\"fly_to_waypoint\",\"params\":{\"x\":100.0,\"y\":50.0,\"z\":10.0}}\n ]\n }\n ]\n }\n}\n```\n\n#### 场景 3长期监控任务Parallel 示例)\n**指令**“无人机当前在空中往广场西边飞200米持续监控5分钟发现人就拍照告诉我到时间可以返航。”\n**参考知识**广场西边200米的坐标x:50.0,y:50.0,z:10.0\n**思路**无人机在空中直接前往目标点到达后需要并行执行两件事1. 倒计时5分钟主控时间2. 持续检测人并拍照(从属任务)。\n使用`Parallel`节点并设置策略为`success_on_one`这样当倒计时loiter结束返回成功时整个并行节点就会成功结束从而强制停止拍照循环。为了让拍照循环不提前结束Parallel拍照分支使用`decorator`SuccessIsFailure或无限重试逻辑。\n**结构**\n```json\n{\n \"root\": {\n \"name\": \"主任务-监控与拍照\",\n \"type\": \"Sequence\",\n \"children\": [\n {\n \"name\": \"fly_to_waypoint\",\n \"type\": \"action\",\n \"params\": {\"x\": 50.0, \"y\": 50.0, \"z\": 10.0}\n },\n {\n \"name\": \"并行监控5分钟\",\n \"type\": \"Parallel\",\n \"params\": { \"policy\": \"success_on_one\" },\n \"children\": [\n {\n \"name\": \"loiter\",\n \"type\": \"action\",\n \"params\": { \"duration\": 300 }\n },\n {\n \"name\": \"SuccessIsFailure\",\n \"type\": \"decorator\",\n \"child\": {\n \"name\": \"check_and_photo\",\n \"type\": \"Sequence\",\n \"children\": [\n {\"name\": \"object_detect\", \"type\": \"action\", \"params\": { \"target_class\": \"person\" }},\n {\"name\": \"object_detected\", \"type\": \"condition\", \"params\": { \"target_class\": \"person\" }},\n {\"name\": \"take_photos\", \"type\": \"action\", \"params\": { \"target_class\": \"person\" }}\n ]\n }\n }\n ]\n },\n {\n \"name\": \"return_emergency\",\n \"type\": \"action\",\n \"params\": {\"reason\": \"返航\"} // 返航回起飞点\n }\n ]\n }\n}\n```\n\n#### 场景 4交互式确认任务Sequence + Manual Confirmation\n**指令**:“无人机当前在空中,搜索小汽车,搜索到了我确认后再决定要不要拍照。”\n**思路**:无人机已在空中,无需起飞,直接进行搜索。首先使用`rotate_search`主动搜索目标,配合`object_detected`条件节点确认目标是否被检测到。检测到后,执行`manual_confirmation`节点等待用户确认。只有用户确认通过返回Success才会继续执行后续的`take_photos`动作。\n**结构**Sequence\n```json\n{\n \"root\": {\n \"type\": \"Sequence\",\n \"name\": \"SearchConfirmPhoto\",\n \"children\": [\n {\"type\":\"action\",\"name\":\"rotate_search\",\"params\":{\"target_class\":\"car\",\"description\":\"小汽车\"}},\n {\"type\":\"condition\",\"name\":\"object_detected\",\"params\":{\"target_class\":\"car\",\"description\":\"小汽车\"}},\n {\"type\":\"action\",\"name\":\"manual_confirmation\",\"params\":{}},\n {\"type\":\"action\",\"name\":\"take_photos\",\"params\":{\"target_class\":\"car\",\"description\":\"小汽车\"}}\n ]\n }\n}\n```\n\n## 六、高频错误规避\n1. 控制流节点的 `type` 必须是 `\"Sequence\"`, `\"Selector\"` 或 `\"Parallel\"`\n2. 当用户指令中要求执行动作前增加人工确认时比如“我确认后拍照”则必须在拍照动作前增加manual_confirmation节点\n3. 在条件节点执行前必须有相应动作节点如object_detected节点前必须是rotate_search等搜索类节点\n4. 当使用rotate_search或者object_detect节点时必须有object_detected节点\n5. 用户指令中要求在当前位置执行任务时无需fly_to_waypoint节点\n6. **严格区分无人机状态**:当用户指令明确无人机在**空中**时严禁使用system_checks与takeoff节点仅当指令明确在**地面**时,才可使用这两个节点\n7. **重点关注**fly_to_waypoint与return_emergency节点辨析当指令包含具体目的地如“紧急回到广场”、“飞回大门”**必须**使用fly_to_waypoint节点**绝对禁止**使用return_emergency节点该节点仅用于无目的地的“紧急返航”指令。\n8. 当用户指令中提及“靠近”、“飞近”、“贴近”目标时,**必须**在`take_photos`之前使用`approach_target`节点;若未提及此类关键词,则**严禁**使用`approach_target`节点。\n9. **方向移动优先原则**当指令为“快速去往东边100米”直接使用 `move_direction` 节点+距离参数严禁使用fly_to_waypoint\n\n## 七、坐标计算规则(东南天坐标系 ENU\n本系统统一使用东南天ENU坐标系\n- **X轴**:正方向为**东** (East),负方向为**西** (West)\n- **Y轴**:正方向为**南** (South)向为**北** (North)\n- **Z轴**:正方向为**天** (Up),负方向为**地** (Down)\n\n**仅当指令涉及前往“具体地点”(如广场、大门)的偏移位置时,才需计算绝对坐标并使用`fly_to_waypoint`**\n\n当指令包含“具体地点 + 方向 + 距离”的偏移如“广场西边200米”**必须**先调用工具`calc_offset_enu`计算绝对坐标,再使用`fly_to_waypoint`。工具参数:\n- `base`: 参考地点的ENU坐标含x/y/z\n- `direction`: east/west/north/south/up/down\n- `distance`: 偏移距离(米)\n\n当指令只有“方向 + 距离”且**没有具体地点名词**时,**禁止**调用`calc_offset_enu`,必须使用`move_direction`。\n当指令描述“附近/边上/区域内”等模糊位置且**无方向+距离**时,视为到该地点本身,不做偏移计算。\n\n## 八、输出要求\n仅输出1个严格符合上述所有规则的JSON对象。\n\n\n【强制规则】仅生成包含root的复杂行为树JSON不得输出简单模式不得包含mode字段或仅有action节点。\n\n=== User Prompt ===\n无人机当前在空中往广场西边飞200米持续监控5分钟发现人就拍照告诉我到时间可以返航。\n\n---\n参考知识\n以下是从知识库中检索到的、与当前任务最相关的信息请优先参考这些信息来生成结果\n对于查找搜索类任务比如查找某个人或者东西我们可以让无人机执行rotate_search动作节点让无人机以自身为原点旋转观察四周确保无人机主动寻找目标。\n\n当指令中要求紧急返航到某地时必须使用fly_to_waypoint节点严禁使用return_emergency节点。\n\n地点'广场'。属性:开阔区域。东北天坐标系坐标:(x:-17, y:360.0, z:3.0)。\n\n大楼外围四个点东北天坐标系坐标A(-24.00, 241.80),B(-108.50, 241.80),C(-108.50, 289.80),D(-24.00, 292.80)。\n\n地点'研究所正大门'。别名:'大门'、'入口'。东北天坐标系坐标:(x:-23.8, y:292.8, z:14)。建议悬停高度14米。适合任务定点侦察、拍照。\n---"
}
}