TaskPulse/backend/app/services/agent.py
Steven 6f64eecb43 fix: heartbeat 500 error, timezone to Beijing, tasks guide collapse
- fix(api): heartbeat endpoint no longer requires request body, fix spa_fallback
  404 handler causing 500 on API routes, add db.refresh() in agent update/heartbeat
- feat(time): unify all frontend time display to Beijing time (Asia/Shanghai)
  via new beijing() utility; backend alert messages also use BJT
- feat(ui): collapse AI agent instruction panel on Tasks page by default
- chore: add backend/app/utils.py and frontend/src/utils/time.js
2026-06-15 03:29:07 +08:00

57 lines
1.9 KiB
Python

"""Agent business logic."""
from sqlalchemy import select, func
from sqlalchemy.ext.asyncio import AsyncSession
from app.models import Agent, ScheduledTask
class AgentService:
def __init__(self, db: AsyncSession):
self.db = db
async def create(self, name: str, description: str = "") -> Agent:
agent = Agent(name=name, description=description)
self.db.add(agent)
await self.db.flush()
await self.db.refresh(agent)
return agent
async def get(self, agent_id: int) -> Agent | None:
return await self.db.get(Agent, agent_id)
async def get_by_api_key(self, api_key: str) -> Agent | None:
stmt = select(Agent).where(Agent.api_key == api_key)
result = await self.db.execute(stmt)
return result.scalar_one_or_none()
async def list_all(self) -> list[Agent]:
stmt = select(Agent).order_by(Agent.id)
result = await self.db.execute(stmt)
return list(result.scalars().all())
async def update(self, agent_id: int, **kwargs) -> Agent | None:
agent = await self.get(agent_id)
if agent is None:
return None
for k, v in kwargs.items():
if v is not None and hasattr(agent, k):
setattr(agent, k, v)
await self.db.flush()
await self.db.refresh(agent)
return agent
async def heartbeat(self, agent_id: int) -> Agent | None:
from datetime import datetime
agent = await self.get(agent_id)
if agent:
agent.last_heartbeat_at = datetime.utcnow()
await self.db.flush()
await self.db.refresh(agent)
return agent
async def get_task_count(self, agent_id: int) -> int:
stmt = select(func.count(ScheduledTask.id)).where(ScheduledTask.agent_id == agent_id)
result = await self.db.execute(stmt)
return result.scalar() or 0