mirror of
https://github.com/Jerryplusy/AI-powered-switches.git
synced 2025-10-14 01:39:18 +00:00
添加端点:获取适配器网段
This commit is contained in:
parent
da5743e27a
commit
fcf072636e
@ -1,3 +1,4 @@
|
||||
import socket
|
||||
from datetime import datetime, timedelta
|
||||
from fastapi import (APIRouter, HTTPException, Response, WebSocket, WebSocketDisconnect)
|
||||
from typing import List
|
||||
@ -7,6 +8,8 @@ from fastapi.responses import HTMLResponse
|
||||
import matplotlib.pyplot as plt
|
||||
import io
|
||||
import base64
|
||||
import psutil
|
||||
import ipaddress
|
||||
|
||||
from ..services.switch_traffic_monitor import get_switch_monitor
|
||||
from ..utils import logger
|
||||
@ -271,7 +274,7 @@ async def get_switch_current_traffic(switch_ip: str, interface: str = None):
|
||||
try:
|
||||
monitor = get_switch_monitor(switch_ip)
|
||||
|
||||
# 如果没有指定接口,获取所有接口的流量
|
||||
|
||||
if not interface:
|
||||
traffic_data = {}
|
||||
for iface in monitor.interface_oids:
|
||||
@ -281,7 +284,6 @@ async def get_switch_current_traffic(switch_ip: str, interface: str = None):
|
||||
"traffic": traffic_data
|
||||
}
|
||||
|
||||
# 获取指定接口的流量
|
||||
return await get_interface_current_traffic(switch_ip, interface)
|
||||
except Exception as e:
|
||||
logger.error(f"获取交换机流量失败: {str(e)}")
|
||||
@ -292,7 +294,7 @@ async def get_interface_current_traffic(switch_ip: str, interface: str) -> dict:
|
||||
"""获取指定交换机接口的当前流量数据"""
|
||||
try:
|
||||
with SessionLocal() as session:
|
||||
# 获取最新记录
|
||||
|
||||
record = session.query(SwitchTrafficRecord).filter(
|
||||
SwitchTrafficRecord.switch_ip == switch_ip,
|
||||
SwitchTrafficRecord.interface == interface
|
||||
@ -327,26 +329,21 @@ async def get_switch_traffic_history(switch_ip: str, interface: str = None, minu
|
||||
try:
|
||||
monitor = get_switch_monitor(switch_ip)
|
||||
|
||||
# 如果没有指定接口,返回所有接口的历史数据
|
||||
if not interface:
|
||||
return {
|
||||
"switch_ip": switch_ip,
|
||||
"history": monitor.get_traffic_history()
|
||||
}
|
||||
|
||||
# 获取指定接口的历史数据
|
||||
with SessionLocal() as session:
|
||||
# 计算时间范围
|
||||
time_threshold = datetime.now() - timedelta(minutes=minutes)
|
||||
|
||||
# 查询历史记录
|
||||
records = session.query(SwitchTrafficRecord).filter(
|
||||
SwitchTrafficRecord.switch_ip == switch_ip,
|
||||
SwitchTrafficRecord.interface == interface,
|
||||
SwitchTrafficRecord.timestamp >= time_threshold
|
||||
).order_by(SwitchTrafficRecord.timestamp.asc()).all()
|
||||
|
||||
# 提取数据
|
||||
history_data = {
|
||||
"in": [record.rate_in for record in records],
|
||||
"out": [record.rate_out for record in records],
|
||||
@ -371,13 +368,10 @@ async def websocket_switch_traffic(websocket: WebSocket, switch_ip: str, interfa
|
||||
monitor = get_switch_monitor(switch_ip)
|
||||
|
||||
while True:
|
||||
# 获取流量数据
|
||||
if interface:
|
||||
# 单个接口
|
||||
traffic_data = await get_interface_current_traffic(switch_ip, interface)
|
||||
await websocket.send_json(traffic_data)
|
||||
else:
|
||||
# 所有接口
|
||||
traffic_data = {}
|
||||
for iface in monitor.interface_oids:
|
||||
traffic_data[iface] = await get_interface_current_traffic(switch_ip, iface)
|
||||
@ -387,7 +381,6 @@ async def websocket_switch_traffic(websocket: WebSocket, switch_ip: str, interfa
|
||||
"traffic": traffic_data
|
||||
})
|
||||
|
||||
# 每秒更新一次
|
||||
await asyncio.sleep(1)
|
||||
except WebSocketDisconnect:
|
||||
logger.info(f"客户端断开交换机流量连接: {switch_ip}")
|
||||
@ -395,22 +388,17 @@ async def websocket_switch_traffic(websocket: WebSocket, switch_ip: str, interfa
|
||||
logger.error(f"交换机流量WebSocket错误: {str(e)}")
|
||||
await websocket.close(code=1011, reason=str(e))
|
||||
|
||||
|
||||
# 交换机流量可视化
|
||||
@router.get("/traffic/switch/plot", response_class=HTMLResponse, summary="交换机流量可视化")
|
||||
async def plot_switch_traffic(switch_ip: str, interface: str, minutes: int = 10):
|
||||
"""生成交换机流量图表"""
|
||||
try:
|
||||
# 获取历史数据
|
||||
history = await get_switch_traffic_history(switch_ip, interface, minutes)
|
||||
history_data = history["history"]
|
||||
|
||||
# 提取数据点
|
||||
time_points = [datetime.fromisoformat(t) for t in history_data["time"]]
|
||||
in_rates = history_data["in"]
|
||||
out_rates = history_data["out"]
|
||||
|
||||
# 创建图表
|
||||
plt.figure(figsize=(12, 6))
|
||||
plt.plot(time_points, in_rates, label="流入流量 (B/s)")
|
||||
plt.plot(time_points, out_rates, label="流出流量 (B/s)")
|
||||
@ -421,8 +409,6 @@ async def plot_switch_traffic(switch_ip: str, interface: str, minutes: int = 10)
|
||||
plt.grid(True)
|
||||
plt.xticks(rotation=45)
|
||||
plt.tight_layout()
|
||||
|
||||
# 转换为HTML图像
|
||||
buf = io.BytesIO()
|
||||
plt.savefig(buf, format="png")
|
||||
buf.seek(0)
|
||||
@ -450,3 +436,29 @@ async def plot_switch_traffic(switch_ip: str, interface: str, minutes: int = 10)
|
||||
except Exception as e:
|
||||
logger.error(f"生成流量图表失败: {str(e)}")
|
||||
return HTMLResponse(content=f"<h1>错误</h1><p>{str(e)}</p>", status_code=500)
|
||||
|
||||
|
||||
@router.get("/network_adapters", summary="获取网络适配器网段")
|
||||
async def get_network_adapters():
|
||||
try:
|
||||
net_if_addrs = psutil.net_if_addrs()
|
||||
|
||||
networks = []
|
||||
for interface, addrs in net_if_addrs.items():
|
||||
for addr in addrs:
|
||||
if addr.family == socket.AF_INET:
|
||||
ip = addr.address
|
||||
netmask = addr.netmask
|
||||
|
||||
network = ipaddress.IPv4Network(f"{ip}/{netmask}", strict=False)
|
||||
networks.append({
|
||||
"adapter": interface,
|
||||
"network": str(network),
|
||||
"ip": ip,
|
||||
"subnet_mask": netmask
|
||||
})
|
||||
|
||||
return {"networks": networks}
|
||||
|
||||
except Exception as e:
|
||||
return {"error": f"获取网络适配器信息失败: {str(e)}"}
|
@ -30,9 +30,9 @@ class AIService:
|
||||
2. 必须包含'commands'字段,包含可直接执行的命令列表
|
||||
3. 其他参数根据配置类型动态添加
|
||||
4. 不要包含解释性文本、步骤说明或注释
|
||||
5.要包含使用ssh连接交换机后的完整命令包括但不完全包括system-view,退出,保存等完整操作
|
||||
5.要包含使用ssh连接交换机后的完整命令包括但不完全包括system-view,退出,保存等完整操作,注意保存还需要输入Y和回车
|
||||
示例命令:'创建VLAN 100,名称为TEST'
|
||||
示例返回:{"type": "vlan", "vlan_id": 100, "name": "TEST", "commands": ["vlan 100", "name TEST"]}
|
||||
示例返回:{"type": "vlan", "vlan_id": 100, "name": "TEST", "commands": ["system-view\n","vlan 100\n", "name TEST\n","quit\n","\x1A\n","save\n","Y\n"]}
|
||||
注意:这里生成的commands中需包含登录交换机和保存等所有操作命令,我们使ssh连接交换机,你不需要给出连接ssh的命令,你只需要给出使用ssh连接到交换机后所输入的全部命令
|
||||
"""
|
||||
|
||||
|
@ -12,7 +12,6 @@ pysnmp==7.1.21
|
||||
aiofiles==23.2.1
|
||||
|
||||
loguru==0.7.2
|
||||
|
||||
tenacity==8.2.3
|
||||
|
||||
asyncio==3.4.3
|
||||
|
Loading…
x
Reference in New Issue
Block a user