feat(voice,agents,memory): voice points get their own branch, agent and keys
This commit is contained in:
@@ -0,0 +1,62 @@
|
||||
"""Единственная ветка голосовых точек: как её открыть и как сменить за ночь."""
|
||||
|
||||
from __future__ import annotations
|
||||
|
||||
import logging
|
||||
from typing import TYPE_CHECKING
|
||||
|
||||
from beaver_agent.voice.texts import KEY, ROTATED, TITLE
|
||||
|
||||
if TYPE_CHECKING:
|
||||
from beaver_gateway.conversations.service import Conversations
|
||||
from beaver_gateway.storage.models import Conversation
|
||||
|
||||
AGENT = "beaver-voice"
|
||||
"""Кто сидит в голосовой ветке; ему не видно ни справки, ни vault."""
|
||||
|
||||
FRONTEND = "voice"
|
||||
TELEGRAM = "telegram"
|
||||
|
||||
_log = logging.getLogger("beaver_agent.voice")
|
||||
|
||||
|
||||
async def current(conversations: Conversations) -> Conversation | None:
|
||||
conv = await conversations.find_bound(frontend=FRONTEND, external_id=KEY)
|
||||
return conv if conv is not None and conv.status == "open" else None
|
||||
|
||||
|
||||
async def open_thread(
|
||||
conversations: Conversations, *, agent: str, window: str | None = None
|
||||
) -> Conversation:
|
||||
"""Завести ветку; без ``window`` окно ей открывает телеграм - новым топиком."""
|
||||
conv = await conversations.spawn(
|
||||
kind="branch",
|
||||
agent=agent,
|
||||
title=TITLE,
|
||||
origin=FRONTEND,
|
||||
binding=(TELEGRAM, window) if window else None,
|
||||
)
|
||||
await conversations.bind(conv, frontend=FRONTEND, external_id=KEY)
|
||||
_log.info("голосовая ветка %s (%s)", conv.external_id, agent)
|
||||
return conv
|
||||
|
||||
|
||||
async def window_of(conversations: Conversations, conv: Conversation) -> str | None:
|
||||
for binding in await conversations.bindings(conv):
|
||||
if binding.frontend == TELEGRAM and binding.visible:
|
||||
return binding.external_id
|
||||
return None
|
||||
|
||||
|
||||
async def rotate(conversations: Conversations) -> Conversation | None:
|
||||
"""Ночью - новая ветка в том же топике; молчавшую за сутки не трогаем."""
|
||||
old = await current(conversations)
|
||||
if old is None or old.last_user_activity_at is None:
|
||||
return None
|
||||
new = await open_thread(
|
||||
conversations, agent=old.agent_name, window=await window_of(conversations, old)
|
||||
)
|
||||
await conversations.close(old)
|
||||
await conversations.say(new, ROTATED)
|
||||
_log.info("голосовая ветка: %s -> %s", old.external_id, new.external_id)
|
||||
return new
|
||||
Reference in New Issue
Block a user