82 lines
2.7 KiB
Python
82 lines
2.7 KiB
Python
|
|
import logging
|
||
|
|
from fastapi import APIRouter, HTTPException
|
||
|
|
from pydantic import BaseModel
|
||
|
|
from typing import Optional
|
||
|
|
|
||
|
|
# 引入 DB 函數
|
||
|
|
from database import (
|
||
|
|
insert_config_backup,
|
||
|
|
get_config_backup_list,
|
||
|
|
get_config_backup_detail,
|
||
|
|
delete_config_backup
|
||
|
|
)
|
||
|
|
|
||
|
|
# ✅ 修正:引入我們剛剛在 cmts_scraper.py 新增的函數
|
||
|
|
from cmts_scraper import fetch_raw_config, parse_config_to_tree
|
||
|
|
|
||
|
|
logger = logging.getLogger(__name__)
|
||
|
|
|
||
|
|
router = APIRouter(
|
||
|
|
prefix="/api/v1/backups",
|
||
|
|
tags=["Backups"]
|
||
|
|
)
|
||
|
|
|
||
|
|
class SnapshotRequest(BaseModel):
|
||
|
|
host: str
|
||
|
|
username: str
|
||
|
|
password: str
|
||
|
|
snapshot_name: str
|
||
|
|
config_type: str = "running"
|
||
|
|
|
||
|
|
@router.get("/", summary="取得歷史快照列表")
|
||
|
|
async def list_backups(host: str, config_type: str = "running"):
|
||
|
|
records = await get_config_backup_list(host, config_type)
|
||
|
|
if records is None:
|
||
|
|
return {"status": "error", "message": "資料庫查詢失敗"}
|
||
|
|
return {"status": "success", "data": records}
|
||
|
|
|
||
|
|
@router.get("/{backup_id}", summary="取得特定快照詳細內容")
|
||
|
|
async def get_backup_detail(backup_id: str):
|
||
|
|
record = await get_config_backup_detail(backup_id)
|
||
|
|
if not record:
|
||
|
|
return {"status": "error", "message": "找不到該筆備份資料"}
|
||
|
|
return {"status": "success", "data": record}
|
||
|
|
|
||
|
|
@router.delete("/{backup_id}", summary="刪除特定快照")
|
||
|
|
async def delete_backup(backup_id: str):
|
||
|
|
success = await delete_config_backup(backup_id)
|
||
|
|
if not success:
|
||
|
|
return {"status": "error", "message": "刪除失敗或找不到該筆資料"}
|
||
|
|
return {"status": "success", "message": "快照已成功刪除"}
|
||
|
|
|
||
|
|
@router.post("/snapshot", summary="手動建立設備快照")
|
||
|
|
async def create_snapshot(req: SnapshotRequest):
|
||
|
|
try:
|
||
|
|
# ✅ 修正:使用函數式呼叫來抓取與解析設定檔
|
||
|
|
raw_cli = await fetch_raw_config(req.host, req.username, req.password, req.config_type)
|
||
|
|
parsed_tree = parse_config_to_tree(raw_cli)
|
||
|
|
|
||
|
|
# 寫入資料庫
|
||
|
|
backup_id = await insert_config_backup(
|
||
|
|
host=req.host,
|
||
|
|
config_type=req.config_type,
|
||
|
|
raw_cli=raw_cli,
|
||
|
|
parsed_tree=parsed_tree,
|
||
|
|
snapshot_name=req.snapshot_name,
|
||
|
|
is_auto=False
|
||
|
|
)
|
||
|
|
|
||
|
|
if not backup_id:
|
||
|
|
return {"status": "error", "message": "資料庫寫入失敗,請檢查系統日誌"}
|
||
|
|
|
||
|
|
return {
|
||
|
|
"status": "success",
|
||
|
|
"message": f"快照 '{req.snapshot_name}' 建立成功!",
|
||
|
|
"backup_id": backup_id
|
||
|
|
}
|
||
|
|
|
||
|
|
except Exception as e:
|
||
|
|
logger.error(f"❌ 建立快照失敗: {e}")
|
||
|
|
return {"status": "error", "message": f"設備連線或解析失敗: {str(e)}"}
|
||
|
|
|