from __future__ import annotations from datetime import datetime, timezone from enum import Enum from typing import Any from pydantic import BaseModel, Field def utc_now_iso() -> str: return datetime.now(timezone.utc).replace(microsecond=0).isoformat() class MeetingType(str, Enum): remote = "remote" in_person = "in_person" hybrid = "hybrid" class RecordingMode(str, Enum): personal_mic = "personal_mic" room_recorder = "room_recorder" class SegmentStatus(str, Enum): uploaded = "uploaded" transcribed = "transcribed" corrected = "corrected" failed = "failed" class MeetingCreate(BaseModel): title: str = "" meeting_type: MeetingType = MeetingType.in_person context: str = "" known_terms: str = "" class SegmentCreate(BaseModel): participant_name: str = "" recording_mode: RecordingMode = RecordingMode.personal_mic room_label: str = "" covered_participants: str = "" class Segment(BaseModel): segment_id: str meeting_id: str label: str participant_name: str = "" recording_mode: RecordingMode = RecordingMode.personal_mic room_label: str = "" covered_participants: list[str] = Field(default_factory=list) created_at: str = Field(default_factory=utc_now_iso) status: SegmentStatus = SegmentStatus.uploaded audio_file_name: str = "" audio_size_bytes: int = 0 audio_duration_seconds: float = 0 audio_format: str = "" audio_channels: int = 0 audio_sample_rate: int = 0 raw_transcript: str = "" corrected_transcript: str = "" error: str = "" class MeetingOutputs(BaseModel): raw_transcript_md: str = "" corrected_transcript_md: str = "" minutes_md: str = "" generated_at: str = "" class Meeting(BaseModel): meeting_id: str host_key: str title: str = "" meeting_type: MeetingType = MeetingType.in_person context: str = "" known_terms: str = "" created_at: str = Field(default_factory=utc_now_iso) updated_at: str = Field(default_factory=utc_now_iso) segments: list[Segment] = Field(default_factory=list) outputs: MeetingOutputs = Field(default_factory=MeetingOutputs) def public_dict(self) -> dict[str, Any]: return { "meeting_id": self.meeting_id, "title": self.title, "meeting_type": self.meeting_type.value, "context": self.context, "known_terms": self.known_terms, "created_at": self.created_at, "updated_at": self.updated_at, "segment_count": len(self.segments), }