Skip to main content

Knowledge > Products > Voice Agent > Tools

Voice Agent Tools

The voice agent exposes tools to the LLM agents so they can take real-world actions during a call: writing to the database, sending SMS messages, and handing off between agents. Every tool is a @function_tool() decorated async method on an Agent subclass. The method receives a RunContext as its second positional argument and accesses call state via self.call_context (a dict containing church_id, church_data, caller_phone, and the Supabase client). The actual DB/SMS logic is split into private _tool_name() helpers in tools.py (imported at call time to avoid circular imports).

SDK: LiveKit Agents v1.5 (livekit.agents). Import: from livekit.agents import RunContext, function_tool.

Tools fall into three categories:

CategoryLocationTools
Church toolsverticals/church/agents.py (@function_tool methods) + verticals/church/tools.py (backend logic)submit_prayer_request, request_callback, capture_visitor_contact, register_for_event, send_giving_link, send_sms_link, send_directions_link
Core tool backendscore/tools.py_send_sms_link, _send_directions_link
Agent handoffverticals/church/agents.pytransfer_to_care (returns new agent instance), end_call
Integration toolsverticals/church/integrations/check_availability, book_appointment (Cal.com), supabase_church helpers (Planning Center)

Tool Pattern

All tools are @function_tool() async methods. There is no background tool concept in LiveKit — all tools return a single value. Context is accessed via self.call_context:

@function_tool()
async def some_tool(self, context: RunContext, param: str) -> dict:
ctx = self.call_context # dict: church_data, caller_phone, supabase, etc.
result = await _some_tool_impl(ctx["supabase"], ctx["church_data"], param)
return result

The context: RunContext parameter is required by the LiveKit SDK but tool logic accesses state through self.call_context, not through context.


Church Tools (verticals/church/agents.py + verticals/church/tools.py)

Tools are @function_tool() methods on CoordinatorAgent and CareAgent. Each method delegates to a private backend function in tools.py (imported inside the method body to avoid circular imports).


1. submit_prayer_request

Available on: Care Agent, Coordinator Agent

Description: Submit a prayer request for the church prayer team.

Parameters:

ParameterTypeRequiredDescription
prayer_textstrYesThe prayer request text
caller_namestrNoCaller's name (blank for anonymous)
is_confidentialboolNoWhether the request is confidential (default: False)

Writes to: voice_prayer_requests

Columns written: church_id, caller_name, caller_phone (from self.call_context), prayer_text, is_confidential, status ("new")

Backend: verticals/church/tools.py:_submit_prayer_request()

Error handling: DB write failure returns a graceful error message. Caller experience is never interrupted.


2. request_callback

Available on: Care Agent, Coordinator Agent

Description: Request a callback from the pastor or church staff.

Parameters:

ParameterTypeRequiredDescription
caller_namestrYesCaller's name
reasonstrYesReason for the callback
preferred_timestrNoPreferred time: morning, afternoon, evening, anytime
phone_numberstrNoOverride phone number (falls back to session caller ID)

Writes to: voice_callback_requests

Columns written: church_id, caller_name, caller_phone, reason, preferred_time, status ("pending")

Backend: verticals/church/tools.py:_request_callback()


3. capture_visitor_contact

Available on: Coordinator Agent

Description: Capture visitor contact info for the welcome team to follow up.

Parameters:

ParameterTypeRequiredDescription
visitor_namestrYesVisitor's name
reason_for_visitstrNoReason for visit interest
emailstrNoVisitor's email address
phone_numberstrNoVisitor's phone number (falls back to session caller ID)

Writes to: voice_visitor_contacts

Columns written: church_id, visitor_name, caller_phone, reason_for_visit, email

Backend: verticals/church/tools.py:_capture_visitor_contact()


4. register_for_event

Available on: Coordinator Agent

Description: Register the caller for a church event. Writes to voice_visitor_contacts with reason_for_visit set to "Event registration: {event_name}".

Parameters:

ParameterTypeRequiredDescription
event_namestrYesTitle of the event to register for
attendee_namestrYesName of person registering
attendee_emailstrNoEmail address
attendee_phonestrNoPhone number (falls back to session caller ID)

Writes to: voice_visitor_contacts (reuses visitor contacts table)

Backend: verticals/church/tools.py:_register_for_event()


Available on: Coordinator Agent

Description: Send an SMS with the church's online giving link.

Parameters: None (uses session caller phone and church_data.giving_url)

Reads from church_data: giving_url

Writes to: Nothing (SMS only, no DB write)

Backend: core/tools.py:_send_sms_link()


Available on: Coordinator Agent, Care Agent

Description: Send any link to the caller via SMS.

Parameters:

ParameterTypeRequiredDescription
urlstrYesThe URL to send
messagestrNoBrief description to include with the link

Backend: core/tools.py:_send_sms_link()


Available on: Coordinator Agent

Description: Send an SMS with a Google Maps link to the church address.

Parameters:

ParameterTypeRequiredDescription
destinationstrNoOverride destination (defaults to church_data.address)

Reads from church_data: address

Backend: core/tools.py:_send_directions_link()


Integration Tools (verticals/church/integrations/)

8. check_availability (Cal.com)

Location: verticals/church/integrations/cal.py

Description: Check available appointment slots for a specific date via Cal.com API v2.

Parameters:

ParameterTypeRequiredDescription
preferred_datestrYesDate to check in YYYY-MM-DD format

Reads from call_context: cal_event_type_id, cal_api_key (from church config)

Precondition: Only wired into the Coordinator's tool list when cal_enabled is true and cal_event_type_id is set.

9. book_appointment (Cal.com)

Location: verticals/church/integrations/cal.py

Description: Book an appointment at an available time slot via Cal.com API v2.

Parameters:

ParameterTypeRequiredDescription
slot_timestrYesISO 8601 start time of the chosen slot
caller_namestrYesName of the person booking
caller_emailstrYesEmail for booking confirmation
caller_phonestrNoPhone number
notesstrNoAny notes for the appointment

Post-booking: Sends a confirmation email to the caller if email provided.

10. Planning Center Helpers

Location: verticals/church/integrations/supabase_church.py

Precondition: Only wired in when pco_enabled is true and both pco_app_id and pco_secret are configured.

HelperDescription
get_service_timesUpcoming service times from PCO Services app
get_upcoming_eventsUpcoming events from PCO Calendar + Services apps
get_staff_directoryStaff/people directory from PCO People app

Agent Handoff Tools

11. transfer_to_care

Available on: Coordinator Agent

Type: Agent handoff — returns a new CareAgent instance (LiveKit SDK auto-handles the handoff when a tool returns an Agent object)

Description: Warm, consent-based handoff to the Care Agent. The Coordinator empathizes first, asks if the caller would like to speak with the Care Agent, and only transfers if the caller agrees.

Returns: (CareAgent instance, "Switching to the Care Agent now.")

When to use: Grief, loss, prayer needs, emotional distress, domestic concerns, sensitive personal topics.

12. end_call

Available on: Coordinator Agent, Care Agent

Description: Graceful call termination. Waits for current TTS to finish playout, then deletes the LiveKit room to end the call.

Implementation: Awaits session.current_speech.wait_for_playout(), then calls job_ctx.api.room.delete_room().


Tool Availability by Agent

ToolCoordinatorCare
submit_prayer_requestYesYes
request_callbackYesYes
capture_visitor_contactYes--
register_for_eventYes--
send_giving_linkYes--
send_sms_linkYesYes
send_directions_linkYes--
transfer_to_careYes--
end_callYesYes
check_availabilityYes*--
book_appointmentYes*--
PCO helpersYes**--

* Only when cal_enabled is true and cal_event_type_id is set ** Only when pco_enabled is true and both pco_app_id and pco_secret are set


Context Injection Pattern

All tools access call state via self.call_context, which is a dict set on the Agent by the session management layer (session.py) before any tools are called:

  • self.call_context["church_id"] -- UUID of the church being served
  • self.call_context["church_data"] -- Full church configuration dict (name, address, giving_url, etc.)
  • self.call_context["caller_phone"] -- Caller's phone number from caller ID
  • self.call_context["supabase"] -- Initialized Supabase async client

The context: RunContext parameter on each @function_tool() method is required by the LiveKit SDK signature but tool logic does not use it directly — all state comes from self.call_context.

All Supabase operations are wrapped in try/except blocks. Failures are logged but never propagate to the caller -- the voice call continues uninterrupted.