Neda/Back/domains/realtime/speaker_service.py
2026-03-06 15:16:41 +03:30

83 lines
1.5 KiB
Python

from sqlalchemy.ext.asyncio import AsyncSession
from db.redis import (
acquire_speaker,
release_speaker,
get_active_speaker
)
from domains.groups.repo import get_group_by_id
from domains.groups.models import GroupType
from integrations.livekit.token_service import generate_join_token
async def request_speak(
db: AsyncSession,
group_id: str,
user_id: str
):
group = await get_group_by_id(db, group_id)
if not group:
return None
# direct chat → no speaker lock
if group.type == GroupType.DIRECT:
token = generate_join_token(
user_id=user_id,
group_id=group_id,
can_publish=True
)
return token
# group chat → push-to-talk
granted = await acquire_speaker(group_id, user_id)
if not granted:
return None
token = generate_join_token(
user_id=user_id,
group_id=group_id,
can_publish=True
)
return token
async def stop_speaking(
db: AsyncSession,
group_id: str,
user_id: str
):
group = await get_group_by_id(db, group_id)
if not group:
return False
# direct chat → nothing to release
if group.type == GroupType.DIRECT:
return True
return await release_speaker(group_id, user_id)
async def current_speaker(
db: AsyncSession,
group_id: str
):
group = await get_group_by_id(db, group_id)
if not group:
return None
if group.type == GroupType.DIRECT:
return None
return await get_active_speaker(group_id)