I am exploring Twilio programmable voice for the first time, and can't find how to get user speech input as text.
TwiML Gather with the speech input
gather: Gather = Gather(
input="speech",
action=process_response_url,
action_on_empty_result=process_response_url,
method="POST",
speech_model="experimental_conversations",
timeout=3,
speech_timeout=3,
max_speech_time=45,
actionOnEmptyResult=True,
)
resp = VoiceResponse()
resp.append(say).append(gather)
return Response(content=resp.to_xml(), media_type="application/xml")
The gather
is executed as expected, and Twilio logs show the request parameters on the action call as
Called=%2B17817024591&ToState=MA&CallerCountry=US&Direction=inbound&SpeechResult=I%27d+like+to+be+a+big+boss.&CallerState=MA&Language=en-US&Confidence=0.905934&ToZip=02062&CallSid=CAf3ffac9dc479ac39f9669b7f0225c963&To=%2B17817024591&CallerZip=02148&ToCountry=US&ApiVersion=2010-04-01&CalledZip=02062&CallStatus=in-progress&CalledCity=NORWOOD&From=%2B17813258707&AccountSid=ACee34277c560b337e8a27d916122afcf8&CalledCountry=US&CallerCity=BOSTON&Caller=%2B17813258707&FromCountry=US&ToCity=NORWOOD&FromCity=BOSTON&CalledState=MA&FromZip=02148&FromState=MA
How can I parse the speechResult parameter? The controller code
@router.post("/process_response", tags=[TWILIO], summary="Process caller response")
async def process_response(request: Request):
print(f"process_response: Request {type(request)}: {request}")
print(f"process_response: path parameters {request.path_params}")
print(f"process_response: query parameters {request.query_params}")
print(f"process_response: values {request.values()}")
Logs show that:
request object is starlette.requests.Request,
request.path_params is an empty dict,
request.query_params is null,
and request.values() returns a ValueView object with various objects and functions, but no parameters
How can I get the parameters?
The SpeechResult and other parameters are available as values on a Form object. Since the caller may not say anything, SpeechResult is an optional parameter, and can be empty, so it is important to provide a default value.
from fastapi import APIRouter, Form, Request
app = FastAPI()
@router.post("/process_response", tags=[TWILIO], summary="Process caller response")
async def process_response(request: Request):
form_data = await request.form()
# Process the SpeechResult
print(f"Received SpeechResult: {form_data['SpeechResult']}")
SpeechResult is a Python string.