113 lines
2.7 KiB
Python
113 lines
2.7 KiB
Python
"""Voice command service — CRUD for user-specific dynamic commands."""
|
|
|
|
from uuid import uuid4
|
|
|
|
from sqlalchemy import select, update
|
|
from sqlalchemy.ext.asyncio import AsyncSession
|
|
|
|
from app.models.voice_command import VoiceCommand
|
|
|
|
|
|
async def list_commands(
|
|
db: AsyncSession,
|
|
user_id: str,
|
|
active_only: bool = True,
|
|
) -> list[dict]:
|
|
stmt = select(VoiceCommand).where(VoiceCommand.user_id == user_id)
|
|
if active_only:
|
|
stmt = stmt.where(VoiceCommand.is_active == True)
|
|
stmt = stmt.order_by(VoiceCommand.count.desc())
|
|
result = await db.execute(stmt)
|
|
return [
|
|
{
|
|
"id": str(c.id),
|
|
"phrase": c.phrase,
|
|
"action": c.action,
|
|
"agent_name": c.agent_name,
|
|
"count": c.count,
|
|
"is_active": c.is_active,
|
|
}
|
|
for c in result.scalars().all()
|
|
]
|
|
|
|
|
|
async def create_command(
|
|
db: AsyncSession,
|
|
user_id: str,
|
|
phrase: str,
|
|
action: str,
|
|
agent_name: str | None = None,
|
|
) -> dict:
|
|
cmd = VoiceCommand(
|
|
id=uuid4(),
|
|
user_id=user_id,
|
|
phrase=phrase,
|
|
action=action,
|
|
agent_name=agent_name,
|
|
count=0,
|
|
is_active=True,
|
|
)
|
|
db.add(cmd)
|
|
await db.commit()
|
|
await db.refresh(cmd)
|
|
return {
|
|
"id": str(cmd.id),
|
|
"phrase": cmd.phrase,
|
|
"action": cmd.action,
|
|
"agent_name": cmd.agent_name,
|
|
"count": cmd.count,
|
|
"is_active": cmd.is_active,
|
|
}
|
|
|
|
|
|
async def increment_command(
|
|
db: AsyncSession,
|
|
command_id: str,
|
|
) -> bool:
|
|
result = await db.execute(
|
|
update(VoiceCommand)
|
|
.where(VoiceCommand.id == command_id)
|
|
.values(count=VoiceCommand.count + 1)
|
|
)
|
|
await db.commit()
|
|
return result.rowcount > 0
|
|
|
|
|
|
async def delete_command(db: AsyncSession, command_id: str, user_id: str) -> bool:
|
|
result = await db.execute(
|
|
select(VoiceCommand).where(
|
|
VoiceCommand.id == command_id,
|
|
VoiceCommand.user_id == user_id,
|
|
)
|
|
)
|
|
cmd = result.scalar_one_or_none()
|
|
if not cmd:
|
|
return False
|
|
await db.delete(cmd)
|
|
await db.commit()
|
|
return True
|
|
|
|
|
|
async def get_suggested_command(
|
|
db: AsyncSession,
|
|
user_id: str,
|
|
min_count: int = 3,
|
|
) -> dict | None:
|
|
"""Find a frequently used command that could be suggested."""
|
|
result = await db.execute(
|
|
select(VoiceCommand)
|
|
.where(VoiceCommand.user_id == user_id)
|
|
.where(VoiceCommand.count >= min_count)
|
|
.where(VoiceCommand.is_active == True)
|
|
.order_by(VoiceCommand.count.desc())
|
|
.limit(1)
|
|
)
|
|
cmd = result.scalar_one_or_none()
|
|
if not cmd:
|
|
return None
|
|
return {
|
|
"phrase": cmd.phrase,
|
|
"action": cmd.action,
|
|
"agent_name": cmd.agent_name,
|
|
}
|