#!/usr/bin/env python # -*- coding: utf-8 -*- """ 任务运行记录API模块 提供任务运行记录相关的API接口 """ from typing import Dict, List, Any, Optional from fastapi import APIRouter, Query, Path, Request from routes.common_api import format_response, error_response from utils.logger import get_logger from services.task_record_service import TaskRecordService from routes.model.task_model import SetTaskErrorRequest # 创建路由 router = APIRouter( prefix="/api/vwed-task-record", tags=["VWED任务运行记录"] ) # router.add_route # 设置日志 logger = get_logger("app.task_record_api") @router.get("/blocks/{task_record_id}") async def get_task_blocks( task_record_id: str = Path(..., description="任务记录ID") ): """ 获取指定任务记录下的所有块运行情况 Args: task_record_id: 任务记录ID,由run_task接口返回的taskRecordId Returns: 包含该任务记录下所有块运行记录的响应 """ try: result = await TaskRecordService.get_task_blocks(task_record_id) if not result["success"]: return error_response(message=result["message"], code=500) return format_response(data=result["data"], message=result["message"]) except Exception as e: logger.error(f"获取任务块运行情况失败: {str(e)}") return error_response(message=f"获取任务块运行情况失败: {str(e)}", code=500) @router.get("/block/{block_record_id}") async def get_block_detail( block_record_id: str = Path(..., description="块记录ID") ): """ 获取指定块记录的详细信息 Args: block_record_id: 块记录ID Returns: 包含该块记录详细信息的响应 """ try: result = await TaskRecordService.get_block_detail(block_record_id) if not result["success"]: return error_response(message=result["message"], code=404) return format_response(data=result["data"], message=result["message"]) except Exception as e: logger.error(f"获取块记录详情失败: {str(e)}") return error_response(message=f"获取块记录详情失败: {str(e)}", code=500) @router.post("/stop/{task_record_id}") async def stop_task_definition(task_record_id: str = Path(..., description="任务记录ID")): """ 停止指定任务记录下的所有运行任务实例,同时禁用定时任务 Args: task_record_id: 任务记录ID Returns: 包含停止结果的响应,包括成功停止的任务数量、是否为定时任务等信息 """ try: # 调用服务层方法 result = await TaskRecordService.stop_task_record(task_record_id) if not result.get("success", False): return error_response( message=result.get("message", "停止任务失败"), code=400 ) return format_response( data=result.get("data", {}), message=result.get("message", "任务终止成功") ) except Exception as e: logger.log_error_with_trace(f"停止任务定义异常", e) return error_response(message=f"任务记录终止失败: {str(e)}", code=500) @router.post("/set-error/{task_record_id}") async def set_task_error( task_record_id: str = Path(..., description="任务记录ID"), request_data: SetTaskErrorRequest = None ): """ 将指定任务记录及其相关任务块状态设置为错误状态 Args: task_record_id: 任务记录ID request_data: 请求数据,包含错误原因 Returns: 包含设置结果的响应,包括任务状态、错误原因、更新的任务块数量等信息 """ try: # 获取错误原因 error_reason = request_data.error_reason if request_data else "未知错误" # 调用服务层方法 result = await TaskRecordService.set_task_error(task_record_id, error_reason) if not result.get("success", False): return error_response( message=result.get("message", "设置任务错误状态失败"), code=400 ) return format_response( data=result.get("data", {}), message=result.get("message", "任务状态设置为错误成功") ) except Exception as e: logger.error(f"设置任务错误状态异常: {str(e)}") return error_response(message=f"设置任务错误状态失败: {str(e)}", code=500) @router.get("/execution/block/results/{task_record_id}") async def get_block_result(task_record_id: str = Path(..., description="任务记录ID")): """ 获取指定任务记录的执行结果 Args: task_record_id: 任务记录ID Returns: 包含执行结果的响应 """ try: result = await TaskRecordService.get_block_results(task_record_id) if not result["success"]: return error_response(message=result["message"], code=404) return format_response(data=result["data"], message=result["message"]) except Exception as e: logger.error(f"获取任务记录执行结果失败: {str(e)}") return error_response(message=f"获取任务记录执行结果失败: {str(e)}", code=500) @router.get("/detail/{task_record_id}") async def get_task_record_detail( task_record_id: str = Path(..., description="任务记录ID") ): """ 获取指定任务记录的详细信息 Args: task_record_id: 任务记录ID Returns: 包含该任务记录详细信息的响应 """ try: result = await TaskRecordService.get_task_record_detail(task_record_id) if not result.get("success", False): return error_response(message=result.get("message", "任务记录不存在"), code=404) return format_response(data=result.get("data", {}), message="成功获取任务记录详情") except Exception as e: logger.error(f"获取任务记录详情失败: {str(e)}") return error_response(message=f"获取任务记录详情失败: {str(e)}", code=500) @router.get("/test") async def test_add_route(): """ 动态添加路由测试 """ # 导入主应用实例 from app import app # 定义新的路由处理函数 def test_handler(): return {"message": "动态添加的路由成功了!"} # 直接在应用实例上添加路由 # 注意:路径必须是绝对路径,包含前缀 full_path = "/api/vwed-task-record/name" # 检查路由是否已存在 route_exists = False for route in app.routes: if getattr(route, "path", "") == full_path: route_exists = True break if not route_exists: app.add_api_route(full_path, test_handler, methods=["GET"]) return {"message": f"路由已添加,请访问 {full_path} 测试"} else: return {"message": f"路由 {full_path} 已存在"} @router.get("/remove-route") async def remove_dynamic_route(route_path: str = Query("/name", description="要删除的路由路径")): """ 删除动态添加的路由 Args: route_path: 要删除的路由路径,不包含前缀,例如 "/name" Returns: 删除结果 """ # 导入主应用实例 from app import app from fastapi.routing import APIRoute # 构建完整路径 if not route_path.startswith("/"): route_path = "/" + route_path full_path = f"/api/vwed-task-record{route_path}" # 查找要删除的路由 route_found = False new_routes = [] for route in app.routes: if getattr(route, "path", "") == full_path: route_found = True continue new_routes.append(route) if route_found: # 替换路由列表 app.router.routes = new_routes # 重新生成路由查找表 app.router.routes_by_name = {} for route in new_routes: if isinstance(route, APIRoute) and route.name: app.router.routes_by_name[route.name] = route return {"success": True, "message": f"路由 {full_path} 已删除"} else: return {"success": False, "message": f"路由 {full_path} 不存在"}