mirror of
https://github.com/Monadical-SAS/reflector.git
synced 2025-12-20 20:29:06 +00:00
- Remove excessive inline comments from meeting creation flow - Remove verbose docstrings from simple property methods and basic functions - Clean up obvious comments like 'Generate JWT tokens', 'Build room URLs' - Remove unnecessary explanatory comments in platform clients - Keep only essential documentation for complex logic - Simplify race condition handling comments - Remove excessive method documentation for simple operations 🤖 Generated with [Claude Code](https://claude.ai/code) Co-Authored-By: Claude <noreply@anthropic.com>
112 lines
3.4 KiB
Python
112 lines
3.4 KiB
Python
import hmac
|
|
from datetime import datetime, timezone
|
|
from hashlib import sha256
|
|
from typing import Any, Dict, Optional
|
|
|
|
import jwt
|
|
|
|
from reflector.db.rooms import Room, VideoPlatform
|
|
from reflector.settings import settings
|
|
from reflector.utils import generate_uuid4
|
|
|
|
from ..base import MeetingData, VideoPlatformClient
|
|
|
|
|
|
class JitsiMeetingData(MeetingData):
|
|
@property
|
|
def user_jwt(self) -> str:
|
|
return self.extra_data.get("user_jwt", "")
|
|
|
|
@property
|
|
def host_jwt(self) -> str:
|
|
return self.extra_data.get("host_jwt", "")
|
|
|
|
@property
|
|
def domain(self) -> str:
|
|
return self.extra_data.get("domain", "")
|
|
|
|
|
|
class JitsiClient(VideoPlatformClient):
|
|
PLATFORM_NAME = VideoPlatform.JITSI
|
|
|
|
def _generate_jwt(self, room: str, moderator: bool, exp: datetime) -> str:
|
|
if not settings.JITSI_JWT_SECRET:
|
|
raise ValueError("JITSI_JWT_SECRET is required for JWT generation")
|
|
|
|
payload = {
|
|
"aud": settings.JITSI_JWT_AUDIENCE,
|
|
"iss": settings.JITSI_JWT_ISSUER,
|
|
"sub": settings.JITSI_DOMAIN,
|
|
"room": room,
|
|
"exp": int(exp.timestamp()),
|
|
"context": {
|
|
"user": {
|
|
"name": "Reflector User",
|
|
"moderator": moderator,
|
|
},
|
|
"features": {
|
|
"recording": True,
|
|
"livestreaming": False,
|
|
},
|
|
},
|
|
}
|
|
|
|
return jwt.encode(payload, settings.JITSI_JWT_SECRET, algorithm="HS256")
|
|
|
|
async def create_meeting(
|
|
self, room_name_prefix: str, end_date: datetime, room: Room
|
|
) -> JitsiMeetingData:
|
|
jitsi_room = f"reflector-{room.name}-{generate_uuid4()}"
|
|
|
|
user_jwt = self._generate_jwt(room=jitsi_room, moderator=False, exp=end_date)
|
|
host_jwt = self._generate_jwt(room=jitsi_room, moderator=True, exp=end_date)
|
|
|
|
room_url = f"https://{settings.JITSI_DOMAIN}/{jitsi_room}?jwt={user_jwt}"
|
|
host_room_url = f"https://{settings.JITSI_DOMAIN}/{jitsi_room}?jwt={host_jwt}"
|
|
|
|
return JitsiMeetingData(
|
|
meeting_id=generate_uuid4(),
|
|
room_name=jitsi_room,
|
|
room_url=room_url,
|
|
host_room_url=host_room_url,
|
|
platform=self.PLATFORM_NAME,
|
|
extra_data={
|
|
"user_jwt": user_jwt,
|
|
"host_jwt": host_jwt,
|
|
"domain": settings.JITSI_DOMAIN,
|
|
},
|
|
)
|
|
|
|
async def get_room_sessions(self, room_name: str) -> Dict[str, Any]:
|
|
return {
|
|
"roomName": room_name,
|
|
"sessions": [
|
|
{
|
|
"sessionId": generate_uuid4(),
|
|
"startTime": datetime.now(tz=timezone.utc).isoformat(),
|
|
"participants": [],
|
|
"isActive": True,
|
|
}
|
|
],
|
|
}
|
|
|
|
async def delete_room(self, room_name: str) -> bool:
|
|
return True
|
|
|
|
async def upload_logo(self, room_name: str, logo_path: str) -> bool:
|
|
return True
|
|
|
|
def verify_webhook_signature(
|
|
self, body: bytes, signature: str, timestamp: Optional[str] = None
|
|
) -> bool:
|
|
if not signature or not self.config.webhook_secret:
|
|
return False
|
|
|
|
try:
|
|
expected = hmac.new(
|
|
self.config.webhook_secret.encode(), body, sha256
|
|
).hexdigest()
|
|
return hmac.compare_digest(expected, signature)
|
|
except Exception:
|
|
return False
|