135 lines
4.8 KiB
Python
135 lines
4.8 KiB
Python
"""管理会计OS — 主入口"""
|
|
import logging
|
|
from fastapi import FastAPI, Request, Depends
|
|
from fastapi.middleware.cors import CORSMiddleware
|
|
from fastapi.responses import JSONResponse
|
|
from dotenv import load_dotenv
|
|
from app.database import init_db
|
|
from app.api import auth, kpis, templates, maps, dashboard, data, alerts, ai_analysis, alert_rules, users, thresholds, notifications, permissions, action_plans, alignment, org, objectives, versions, budget, cost, predict, reports, security, knowledge, bot_bridge, customer_dashboard, deviation_push, budget_generate, knowledge_articles, kpi_causality, data_quality, bi_reports, entities, bsc_layers, okr, okr_templates, subjects, driver_budget
|
|
from app.utils.cache import clear_all as clear_cache, delete as delete_cache
|
|
from scripts.erp_sync import run_sync as run_erp_sync
|
|
from app.auth_middleware import require_auth
|
|
|
|
load_dotenv()
|
|
|
|
# 日志配置
|
|
logging.basicConfig(
|
|
level=logging.INFO,
|
|
format="%(asctime)s [%(levelname)s] %(name)s: %(message)s",
|
|
datefmt="%Y-%m-%d %H:%M:%S",
|
|
)
|
|
logger = logging.getLogger("cma")
|
|
|
|
app = FastAPI(title="管理会计OS API", version="1.0.0", docs_url="/docs")
|
|
|
|
app.add_middleware(
|
|
CORSMiddleware,
|
|
allow_origins=["*"],
|
|
allow_credentials=True,
|
|
allow_methods=["*"],
|
|
allow_headers=["*"],
|
|
)
|
|
|
|
app.include_router(auth.router)
|
|
app.include_router(kpis.router)
|
|
app.include_router(templates.router)
|
|
app.include_router(maps.router)
|
|
app.include_router(dashboard.router)
|
|
app.include_router(data.router)
|
|
app.include_router(alerts.router)
|
|
app.include_router(ai_analysis.router)
|
|
app.include_router(alert_rules.router)
|
|
app.include_router(users.router)
|
|
app.include_router(thresholds.router)
|
|
app.include_router(notifications.router)
|
|
app.include_router(permissions.router)
|
|
app.include_router(action_plans.router)
|
|
app.include_router(alignment.router)
|
|
app.include_router(org.router)
|
|
app.include_router(objectives.router)
|
|
app.include_router(versions.router)
|
|
app.include_router(budget.router)
|
|
app.include_router(cost.router)
|
|
app.include_router(predict.router)
|
|
app.include_router(reports.router)
|
|
app.include_router(security.router)
|
|
app.include_router(knowledge.router)
|
|
app.include_router(bot_bridge.router)
|
|
app.include_router(customer_dashboard.router)
|
|
app.include_router(deviation_push.router)
|
|
app.include_router(budget_generate.router)
|
|
app.include_router(knowledge_articles.router)
|
|
app.include_router(kpi_causality.router)
|
|
app.include_router(data_quality.router)
|
|
app.include_router(bi_reports.router)
|
|
app.include_router(entities.router)
|
|
app.include_router(bsc_layers.router)
|
|
app.include_router(okr.router)
|
|
app.include_router(okr_templates.router)
|
|
app.include_router(subjects.router)
|
|
app.include_router(driver_budget.router)
|
|
|
|
@app.exception_handler(Exception)
|
|
async def global_exception_handler(request: Request, exc: Exception):
|
|
logger.error(f"未捕获异常: {exc}", exc_info=True)
|
|
return JSONResponse(status_code=500, content={"detail": "服务器内部错误"})
|
|
|
|
|
|
@app.on_event("startup")
|
|
def startup():
|
|
init_db()
|
|
logger.info("管理会计OS后端启动完成")
|
|
|
|
|
|
@app.post("/api/cma/admin/erp-sync")
|
|
def admin_erp_sync(user=Depends(require_auth), kpi_codes: str = None):
|
|
"""手动触发ERP数据同步"""
|
|
kpi_list = kpi_codes.split(",") if kpi_codes else None
|
|
try:
|
|
run_erp_sync(dry_run=False, kpi_codes=kpi_list, use_api=True)
|
|
return {"message": "ERP同步完成", "kpis": kpi_list}
|
|
except Exception as e:
|
|
return JSONResponse(status_code=500, content={"detail": f"同步失败: {str(e)}"})
|
|
|
|
|
|
@app.get("/api/cma/admin/erp-sync/dry-run")
|
|
def admin_erp_sync_dry_run(user=Depends(require_auth), kpi_codes: str = None):
|
|
"试运行,不写入数据库"""
|
|
kpi_list = kpi_codes.split(",") if kpi_codes else None
|
|
try:
|
|
run_erp_sync(dry_run=True, kpi_codes=kpi_list, use_api=True)
|
|
return {"message": "试运行完成"}
|
|
except Exception as e:
|
|
return JSONResponse(status_code=500, content={"detail": f"试运行失败: {str(e)}"})
|
|
|
|
|
|
@app.post("/api/cma/admin/alerts/check")
|
|
def admin_check_alerts():
|
|
"""手动触发预警检查"""
|
|
from app.database import get_session_local
|
|
from scripts.alert_generator import generate_and_push
|
|
db = get_session_local()()
|
|
try:
|
|
result = generate_and_push(db)
|
|
return {"message": "预警检查完成", "result": result}
|
|
except Exception as e:
|
|
return JSONResponse(status_code=500, content={"detail": f"检查失败: {str(e)}"})
|
|
finally:
|
|
db.close()
|
|
|
|
|
|
@app.post("/api/cma/admin/cache/clear")
|
|
def admin_clear_cache(module: str = None):
|
|
"""清空缓存,指定module则只清该模块"""
|
|
if module:
|
|
delete_cache(module)
|
|
return {"message": f"缓存已清空: {module}"}
|
|
else:
|
|
clear_cache()
|
|
return {"message": "全部缓存已清空"}
|
|
|
|
|
|
@app.get("/health")
|
|
def health():
|
|
return {"status": "ok", "version": "1.0.0"}
|