Merge pull request #2954 from pipecat-ai/mb/runner-meeting-token-properties

Add support for token properties in Daily util and development runner
This commit is contained in:
Mark Backman
2025-10-31 12:12:14 -04:00
committed by GitHub
3 changed files with 41 additions and 7 deletions

View File

@@ -164,9 +164,10 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
### Changed
- The development runner's `/start` endpoint now supports passing
`dailyRoomProperties` in the request body when `createDailyRoom` is true.
Properties are validated against the `DailyRoomProperties` type and passed to
Daily's room creation API.
`dailyRoomProperties` and `dailyMeetingTokenProperties` in the request body
when `createDailyRoom` is true. Properties are validated against the
`DailyRoomProperties` and `DailyMeetingTokenProperties` types respectively
and passed to Daily's room and token creation APIs.
- `UserImageRawFrame` new fields `append_to_context` and `text`. The
`append_to_context` field indicates if this image and text should be added to

View File

@@ -44,6 +44,8 @@ from loguru import logger
from pydantic import BaseModel
from pipecat.transports.daily.utils import (
DailyMeetingTokenParams,
DailyMeetingTokenProperties,
DailyRESTHelper,
DailyRoomParams,
DailyRoomProperties,
@@ -84,6 +86,7 @@ async def configure(
sip_num_endpoints: Optional[int] = 1,
sip_codecs: Optional[Dict[str, List[str]]] = None,
room_properties: Optional[DailyRoomProperties] = None,
token_properties: Optional["DailyMeetingTokenProperties"] = None,
) -> DailyRoomConfig:
"""Configure Daily room URL and token with optional SIP capabilities.
@@ -106,6 +109,9 @@ async def configure(
individual parameters. When provided, this overrides room_exp_duration and
SIP-related parameters. If not provided, properties are built from the
individual parameters as before.
token_properties: Optional DailyMeetingTokenProperties to customize the meeting
token. When provided, these properties are passed to the token creation API.
Note that room_name, exp, and is_owner will be set automatically.
Returns:
DailyRoomConfig: Object with room_url, token, and optional sip_endpoint.
@@ -179,7 +185,10 @@ async def configure(
# Create token and return standard format
expiry_time: float = token_exp_duration * 60 * 60
token = await daily_rest_helper.get_token(room_url, expiry_time)
token_params = None
if token_properties:
token_params = DailyMeetingTokenParams(properties=token_properties)
token = await daily_rest_helper.get_token(room_url, expiry_time, params=token_params)
return DailyRoomConfig(room_url=room_url, token=token)
# Create a new room
@@ -221,7 +230,12 @@ async def configure(
# Create meeting token
token_expiry_seconds = token_exp_duration * 60 * 60
token = await daily_rest_helper.get_token(room_url, token_expiry_seconds)
token_params = None
if token_properties:
token_params = DailyMeetingTokenParams(properties=token_properties)
token = await daily_rest_helper.get_token(
room_url, token_expiry_seconds, params=token_params
)
if sip_enabled:
# Return SIP configuration object

View File

@@ -555,6 +555,7 @@ def _setup_daily_routes(app: FastAPI):
{
"createDailyRoom": true,
"dailyRoomProperties": { "start_video_off": true },
"dailyMeetingTokenProperties": { "is_owner": true, "user_name": "Bot" },
"body": { "custom_data": "value" }
}
"""
@@ -571,6 +572,7 @@ def _setup_daily_routes(app: FastAPI):
create_daily_room = request_data.get("createDailyRoom", False)
body = request_data.get("body", {})
daily_room_properties_dict = request_data.get("dailyRoomProperties", None)
daily_token_properties_dict = request_data.get("dailyMeetingTokenProperties", None)
bot_module = _get_bot_module()
@@ -585,7 +587,10 @@ def _setup_daily_routes(app: FastAPI):
import aiohttp
from pipecat.runner.daily import configure
from pipecat.transports.daily.utils import DailyRoomProperties
from pipecat.transports.daily.utils import (
DailyMeetingTokenProperties,
DailyRoomProperties,
)
async with aiohttp.ClientSession() as session:
# Parse dailyRoomProperties if provided
@@ -598,7 +603,21 @@ def _setup_daily_routes(app: FastAPI):
logger.error(f"Failed to parse dailyRoomProperties: {e}")
# Continue without custom properties
room_url, token = await configure(session, room_properties=room_properties)
# Parse dailyMeetingTokenProperties if provided
token_properties = None
if daily_token_properties_dict:
try:
token_properties = DailyMeetingTokenProperties(
**daily_token_properties_dict
)
logger.debug(f"Using custom token properties: {token_properties}")
except Exception as e:
logger.error(f"Failed to parse dailyMeetingTokenProperties: {e}")
# Continue without custom properties
room_url, token = await configure(
session, room_properties=room_properties, token_properties=token_properties
)
runner_args = DailyRunnerArguments(room_url=room_url, token=token, body=body)
result = {
"dailyRoom": room_url,