diff --git a/src/backend/README.md b/src/backend/README.md index cc340a6..0a34790 100644 --- a/src/backend/README.md +++ b/src/backend/README.md @@ -1,7 +1,7 @@ # AI-powered-switches Backend 这是 AI-powered-switches 的后端服务,基于 `Flask` 构建,提供 `REST API` 接口,用于解析自然语言生成网络交换机配置并下发到设备 - +注意下载Nmap才可扫描交换机网址:https://nmap.org/download.html ### 项目结构 ```bash diff --git a/src/backend/app/api/endpoints.py b/src/backend/app/api/endpoints.py index c5d3678..917bb2a 100644 --- a/src/backend/app/api/endpoints.py +++ b/src/backend/app/api/endpoints.py @@ -1,4 +1,4 @@ -from fastapi import APIRouter, Depends, HTTPException +from fastapi import (APIRouter, HTTPException) from typing import List from pydantic import BaseModel @@ -86,4 +86,5 @@ async def apply_config(request: ConfigRequest): raise HTTPException( status_code=500, detail=f"Failed to apply config: {str(e)}" - ) \ No newline at end of file + ) + diff --git a/src/backend/app/api/network_config.py b/src/backend/app/api/network_config.py index 3f791c2..ebc1b82 100644 --- a/src/backend/app/api/network_config.py +++ b/src/backend/app/api/network_config.py @@ -1,8 +1,11 @@ import paramiko import asyncio +import aiofiles +from datetime import datetime from typing import Dict, List, Optional, Union from tenacity import retry, stop_after_attempt, wait_exponential, retry_if_exception_type from pydantic import BaseModel +from paramiko.channel import ChannelFile import logging @@ -41,6 +44,7 @@ class SwitchConfigurator: is_emulated: bool = False, emulated_delay: float = 2.0 ): + """ 初始化配置器 diff --git a/src/backend/app/utils/exceptions.py b/src/backend/app/utils/exceptions.py index 4108d08..ccbd2de 100644 --- a/src/backend/app/utils/exceptions.py +++ b/src/backend/app/utils/exceptions.py @@ -1,4 +1,5 @@ from fastapi import HTTPException, status +from typing import Optional class AICommandParseException(HTTPException): def __init__(self, detail: str): @@ -8,15 +9,28 @@ class AICommandParseException(HTTPException): ) class SwitchConfigException(HTTPException): - def __init__(self, detail: str): + def __init__( + self, + detail: str, + status_code: int = status.HTTP_500_INTERNAL_SERVER_ERROR + ): super().__init__( - status_code=status.HTTP_500_INTERNAL_SERVER_ERROR, - detail=f"Switch configuration error: {detail}" + status_code=status_code, + detail=f"Switch error: {detail}" ) -class SiliconFlowAPIException(HTTPException): - def __init__(self, detail: str): +class ConfigBackupException(SwitchConfigException): + """配置备份失败异常""" + def __init__(self, ip: str): super().__init__( - status_code=status.HTTP_503_SERVICE_UNAVAILABLE, - detail=f"SiliconFlow API error: {detail}" - ) \ No newline at end of file + detail=f"无法备份设备 {ip} 的配置", + recovery_guide="检查设备存储空间或权限" + ) + +class ConfigRollbackException(SwitchConfigException): + """回滚失败异常""" + def __init__(self, ip: str, original_error: str): + super().__init__( + detail=f"设备 {ip} 回滚失败(原始错误:{original_error})", + status_code=status.HTTP_422_UNPROCESSABLE_ENTITY + ) diff --git a/src/backend/requirements.txt b/src/backend/requirements.txt index 4ca45f3..916c9ce 100644 --- a/src/backend/requirements.txt +++ b/src/backend/requirements.txt @@ -7,4 +7,5 @@ pydantic>=1.10.7 loguru>=0.7.0 python-nmap>=0.7.1 tenacity>=9.1.2 -typing-extensions>=4.0.0 \ No newline at end of file +typing-extensions>=4.0.0 +aiofiles>=24.1.0 \ No newline at end of file diff --git a/switch_devices.json b/switch_devices.json new file mode 100644 index 0000000..0637a08 --- /dev/null +++ b/switch_devices.json @@ -0,0 +1 @@ +[] \ No newline at end of file