DEV Community

Cover image for Building Aarogya Sahayak: My 10-Day Journey Building a Voice AI Health Assistant
Vishal Kumar
Vishal Kumar

Posted on

Building Aarogya Sahayak: My 10-Day Journey Building a Voice AI Health Assistant

๐…๐ซ๐จ๐ฆ ๐š ๐›๐š๐ฌ๐ข๐œ ๐ฏ๐จ๐ข๐œ๐ž ๐š๐ฌ๐ฌ๐ข๐ฌ๐ญ๐š๐ง๐ญ ๐ญ๐จ ๐ก๐ฎ๐ฆ๐š๐ง ๐ž๐ฌ๐œ๐š๐ฅ๐š๐ญ๐ข๐จ๐ง, ๐œ๐š๐ฅ๐ฅ ๐š๐ง๐š๐ฅ๐ฒ๐ญ๐ข๐œ๐ฌ, ๐ฆ๐ฎ๐ฅ๐ญ๐ข๐ฅ๐ข๐ง๐ ๐ฎ๐š๐ฅ ๐œ๐จ๐ง๐ฏ๐ž๐ซ๐ฌ๐š๐ญ๐ข๐จ๐ง๐ฌ, ๐š๐ง๐ ๐ฌ๐ฉ๐ž๐œ๐ข๐š๐ฅ๐ข๐ฌ๐ญ ๐ก๐š๐ง๐๐จ๐Ÿ๐Ÿ๐ฌ.

๐Ÿ. ๐“๐ก๐ž ๐๐ซ๐จ๐›๐ฅ๐ž๐ฆ ๐š๐ง๐ ๐ญ๐ก๐ž ๐”๐ฌ๐ž๐ซ๐ฌ

Healthcare can be difficult to navigate, especially when users are not sure whether they need general health guidance, a clinic appointment, or support from a real person.

For this project, I chose the Health Access track and built "๐€๐š๐ซ๐จ๐ ๐ฒ๐š ๐’๐š๐ก๐š๐ฒ๐š๐ค", a voice-based health and wellness assistant designed to make basic health conversations easier and more accessible.

The idea was not to build an AI doctor or replace medical professionals. Instead, "๐€๐š๐ซ๐จ๐ ๐ฒ๐š ๐’๐š๐ก๐š๐ฒ๐š๐ค" is designed to help users with general health and wellness questions, guide them toward appropriate next steps, and connect them with human support when a situation requires it.

I chose voice because users can speak naturally instead of typing everything into a chat box. This makes the interaction feel more like a real conversation and can be especially useful for people who prefer speaking over typing.

The project also focuses on safety. When a conversation involves diagnosis requests, emergency or red-flag situations, or needs human intervention, the agent follows dedicated safety and escalation flows instead of trying to handle everything itself.

The assistant also supports scheduled reminder calls, allowing users to request reminders naturally and receive a follow-up call at the requested time. This extends the experience beyond a single conversation while keeping the existing safety and consent rules in place.

๐Ÿ. ๐–๐ก๐š๐ญ ๐ญ๐ก๐ž ๐•๐จ๐ข๐œ๐ž ๐€๐ ๐ž๐ง๐ญ ๐ƒ๐จ๐ž๐ฌ

๐€๐š๐ซ๐จ๐ ๐ฒ๐š ๐’๐š๐ก๐š๐ฒ๐š๐ค is built as a conversational voice assistant rather than a simple question-and-answer bot.

A user can start a natural conversation about general health and wellness. The main agent can provide basic guidance while following clear safety boundaries. It does not try to diagnose medical conditions or act as a replacement for a healthcare professional.

  • ๐—Ÿ๐—ฎ๐—ป๐—ด๐˜‚๐—ฎ๐—ด๐—ฒ ๐—ฆ๐—ฒ๐—น๐—ฒ๐—ฐ๐˜๐—ถ๐—ผ๐—ป

One of the important improvements I added was a language-selection flow.

Before starting a conversation, the user can choose between "๐—˜๐—ป๐—ด๐—น๐—ถ๐˜€๐—ต" ๐—ฎ๐—ป๐—ฑ "๐—›๐—ถ๐—ป๐—ฑ๐—ถ". Once selected, the preferred language is carried through the agent session so the conversation stays consistent instead of randomly switching languages.

For Hindi conversations, the agent is instructed to respond using "๐——๐—ฒ๐˜ƒ๐—ฎ๐—ป๐—ฎ๐—ด๐—ฎ๐—ฟ๐—ถ ๐˜€๐—ฐ๐—ฟ๐—ถ๐—ฝ๐˜" rather than Romanized Hindi. This makes the conversation more natural for users who prefer reading and speaking Hindi.

  • ๐—›๐˜‚๐—บ๐—ฎ๐—ป ๐—ฆ๐˜‚๐—ฝ๐—ฝ๐—ผ๐—ฟ๐˜

When a situation needs human assistance, ๐€๐š๐ซ๐จ๐ ๐ฒ๐š ๐’๐š๐ก๐š๐ฒ๐š๐ค can create a human support request and provide a unique reference ID.

The user can later use that reference ID on the Human Support page to check the status of the request.

The public support page is intentionally privacy-focused. It displays only safe request metadata such as the reference ID, status, timestamps, urgency, and follow-up information. Conversation content and sensitive health details are not exposed on the public page.

  • ๐—ฆ๐—ฝ๐—ฒ๐—ฐ๐—ถ๐—ฎ๐—น๐—ถ๐˜€๐˜ ๐—”๐—ด๐—ฒ๐—ป๐˜ ๐—›๐—ฎ๐—ป๐—ฑ๐—ผ๐—ณ๐—ณ

Another important feature is the "๐—–๐—น๐—ถ๐—ป๐—ถ๐—ฐ & ๐—”๐—ฝ๐—ฝ๐—ผ๐—ถ๐—ป๐˜๐—บ๐—ฒ๐—ป๐˜ ๐—ฆ๐—ฝ๐—ฒ๐—ฐ๐—ถ๐—ฎ๐—น๐—ถ๐˜€๐˜".

When a user clearly wants to book or prepare for a clinic appointment, the main agent can hand the conversation to this dedicated specialist instead of trying to handle every task itself.

The specialist can help with appointment-related questions, preparation, preferred appointment timing, and general visit guidance.

The user does not have to repeat the entire problem because relevant context is transferred during the handoff.

  • ๐—ฆ๐—ฝ๐—ฒ๐—ฐ๐—ถ๐—ฎ๐—น๐—ถ๐˜€๐˜ ๐—›๐—ฎ๐—ป๐—ฑ๐—ฏ๐—ฎ๐—ฐ๐—ธ

The specialist can also hand the conversation back to the main health assistant when the appointment-related task is complete or when the user wants to discuss a general health topic.

This creates a simple multi-agent flow where each agent has a focused responsibility.

  • ๐—–๐—ฎ๐—น๐—น ๐—”๐—ป๐—ฎ๐—น๐˜†๐˜๐—ถ๐—ฐ๐˜€

I also built a Call Analytics Dashboard to make the voice agent measurable instead of relying only on how the conversation feels.

The dashboard tracks real call outcomes such as:

  • Total calls
  • Successful calls
  • Failed calls
  • Call outcome trends

The success and failure logic is connected to actual call outcomes rather than hardcoded numbers.

This helped me understand whether the agent was actually completing useful conversations.

  • ๐—ฆ๐—ฐ๐—ต๐—ฒ๐—ฑ๐˜‚๐—น๐—ฒ๐—ฑ ๐—ฅ๐—ฒ๐—บ๐—ถ๐—ป๐—ฑ๐—ฒ๐—ฟ ๐—–๐—ฎ๐—น๐—น๐˜€

A new feature I added is scheduled reminder calling.

Users can ask the agent to schedule a reminder naturally, such as "Remind me in 5 minutes to drink water." The agent understands relative or specific times, validates the requested timezone when needed, and creates a reminder with a unique reference ID.

The reminder is processed by the existing outbound calling system instead of using a separate dialing implementation. An exactly-once mechanism prevents the same reminder from being dialed multiple times.

Users can also open the Scheduled Reminders page to check the reminder status and cancel a reminder while it is still pending.

  • ๐—ช๐—ฒ๐—น๐—น๐—ป๐—ฒ๐˜€๐˜€ ๐—ง๐—ถ๐—ฝ๐˜€

I also added a dedicated Wellness Tips section for users who want simple general wellness guidance outside the live conversation.

It includes five areas:

  • Hydration
  • Sleep & Rest
  • Healthy Eating
  • Daily Activity
  • Stress & Relaxation

The section is designed for general wellness information and includes a clear disclaimer that it is not medical advice.

๐Ÿ‘.๐‡๐จ๐ฐ ๐ญ๐ก๐ž ๐’๐ฒ๐ฌ๐ญ๐ž๐ฆ ๐–๐จ๐ซ๐ค๐ฌ

๐€๐š๐ซ๐จ๐ ๐ฒ๐š ๐’๐š๐ก๐š๐ฒ๐š๐ค is built around a real-time voice conversation pipeline. The goal was to keep the interaction simple for the user while allowing different parts of the system to handle different responsibilities.

At a high level, the flow looks like this:

  • ๐Ÿญ.๐—จ๐˜€๐—ฒ๐—ฟ ๐—ฎ๐—ป๐—ฑ ๐—™๐—ฟ๐—ผ๐—ป๐˜๐—ฒ๐—ป๐—ฑ The user starts the conversation from the web interface and can choose their preferred language before the voice session begins.

The frontend handles the conversation interface, voice controls, language selection, agent status, and other user-facing states.

  • ๐Ÿฎ.๐—ฅ๐—ฒ๐—ฎ๐—น-๐—ง๐—ถ๐—บ๐—ฒ ๐—ฉ๐—ผ๐—ถ๐—ฐ๐—ฒ ๐—ง๐—ฟ๐—ฎ๐—ป๐˜€๐—ฝ๐—ผ๐—ฟ๐˜ The voice conversation runs through "๐—Ÿ๐—ถ๐˜ƒ๐—ฒ๐—ž๐—ถ๐˜", which provides the real-time communication layer between the user and the agent.

This allows the agent to receive the user's audio, process it, and return spoken responses during the same conversation.

  • ๐Ÿฏ. ๐—ฆ๐—ฝ๐—ฒ๐—ฒ๐—ฐ๐—ต-๐˜๐—ผ-๐—ง๐—ฒ๐˜…๐˜ When the user speaks, their audio is converted into text so the language model can understand the request.

This text becomes the input for the agent's reasoning and routing logic.

  • ๐Ÿฐ.๐— ๐—ฎ๐—ถ๐—ป ๐—”๐—ด๐—ฒ๐—ป๐˜ The main ๐€๐š๐ซ๐จ๐ ๐ฒ๐š ๐’๐š๐ก๐š๐ฒ๐š๐ค agent is responsible for general health and wellness conversations.

It follows a system prompt containing its role, objectives, safety rules, language instructions, and routing decisions.

The main agent does not try to handle every request itself. Depending on the conversation, it can use tools or hand the conversation to another part of the system.

  • ๐Ÿฑ. ๐—ง๐—ผ๐—ผ๐—น๐˜€ ๐—ฎ๐—ป๐—ฑ ๐—ฅ๐—ผ๐˜‚๐˜๐—ถ๐—ป๐—ด The agent can use dedicated tools when a task requires an action rather than a simple response.

For example, a clear clinic or appointment request can trigger a handoff to the "Clinic & Appointment Specialist".

Emergency or red-flag situations follow the existing escalation flow instead of being sent to the appointment specialist.

This separation keeps the responsibilities of each agent clear.

  • ๐Ÿฒ.๐—ฆ๐—ฐ๐—ต๐—ฒ๐—ฑ๐˜‚๐—น๐—ฒ๐—ฑ ๐—ฅ๐—ฒ๐—บ๐—ถ๐—ป๐—ฑ๐—ฒ๐—ฟ ๐—™๐—น๐—ผ๐˜„

The agent can also create scheduled reminders from natural-language requests.

When a user asks for a reminder, the request is parsed and stored with a unique reference ID. The scheduler checks for due reminders and triggers the existing outbound calling system at the scheduled time.

The reminder system uses an exactly-once claiming mechanism to prevent duplicate calls. Users can also check the reminder status or cancel a reminder while it is still pending.

This flow reuses the existing outbound dialer instead of introducing a separate calling system.

  • ๐Ÿณ.๐—ฆ๐—ฝ๐—ฒ๐—ฐ๐—ถ๐—ฎ๐—น๐—ถ๐˜€๐˜ ๐—”๐—ด๐—ฒ๐—ป๐˜ The Clinic & Appointment Specialist is a separate agent with its own instructions and responsibilities.

During a handoff, only relevant context is transferred instead of exposing the entire conversation unnecessarily.

The specialist can continue the conversation without asking the user to repeat the original request.

When its task is complete or the user changes back to a general health topic, the specialist can hand the conversation back to the main agent.

  • ๐Ÿด.๐—ง๐—ฒ๐˜…๐˜-๐˜๐—ผ-๐—ฆ๐—ฝ๐—ฒ๐—ฒ๐—ฐ๐—ต After the agent generates a response, it is converted back into speech so the user can hear the answer naturally.

For this project, I used "๐— ๐˜‚๐—ฟ๐—ณ ๐—™๐—ฎ๐—น๐—ฐ๐—ผ๐—ป" for the voice experience.

One of the things I wanted to achieve was a conversational experience that feels closer to talking to an assistant rather than interacting with a traditional text chatbot.

Architecture Overview

The overall architecture can be represented as:

๐Ÿ’. ๐“๐ก๐ž ๐Œ๐จ๐ฌ๐ญ ๐ˆ๐ฆ๐ฉ๐จ๐ซ๐ญ๐š๐ง๐ญ ๐…๐ž๐š๐ญ๐ฎ๐ซ๐ž๐ฌ

Over the course of the challenge, I gradually added features that made "Aarogya Sahayak" more useful, safer, and easier to evaluate.

  • ๐—ฆ๐—ฎ๐—ณ๐—ฒ๐˜๐˜† ๐—š๐˜‚๐—ฎ๐—ฟ๐—ฑ๐—ฟ๐—ฎ๐—ถ๐—น๐˜€ The agent has clear boundaries around what it can and cannot do.

It is designed for general health and wellness guidance, not medical diagnosis. Emergency or red-flag situations follow a separate escalation flow instead of being routed to the appointment specialist.

The agent also avoids asking users for sensitive information such as passwords, OTPs, PINs, or card details.

๐Ÿญ.๐—›๐˜‚๐—บ๐—ฎ๐—ป ๐—˜๐˜€๐—ฐ๐—ฎ๐—น๐—ฎ๐˜๐—ถ๐—ผ๐—ป
When a conversation needs human intervention, the agent can create a support request and generate a unique reference ID.

The user can use this ID to check the request status later through the Human Support page.

The public status page is intentionally privacy-focused and does not expose the user's conversation or sensitive health information.

๐Ÿฎ.๐—–๐—น๐—ถ๐—ป๐—ถ๐—ฐ ๐—ฎ๐—ป๐—ฑ ๐—”๐—ฝ๐—ฝ๐—ผ๐—ถ๐—ป๐˜๐—บ๐—ฒ๐—ป๐˜ ๐—ฆ๐—ฝ๐—ฒ๐—ฐ๐—ถ๐—ฎ๐—น๐—ถ๐˜€๐˜
Instead of making the main agent responsible for everything, I created a dedicated "Clinic & Appointment Specialist".

The specialist focuses on appointment-related tasks such as:

  • Understanding appointment requests
  • Helping with clinic visit preparation
  • Discussing preferred appointment timing
  • Providing general appointment guidance

The main agent announces the handoff before switching the conversation, and the specialist introduces itself after taking over.

๐Ÿฏ.๐—ฆ๐—ฝ๐—ฒ๐—ฐ๐—ถ๐—ฎ๐—น๐—ถ๐˜€๐˜ ๐—›๐—ฎ๐—ป๐—ฑ๐—ฏ๐—ฎ๐—ฐ๐—ธ
The specialist can also return the conversation to the main health assistant.

For example, if the user finishes discussing an appointment and asks for general wellness advice, the specialist can hand the conversation back instead of continuing outside its scope.

Relevant context is preserved during both handoff and handback so the user does not have to repeat everything.

๐Ÿฐ.๐— ๐˜‚๐—น๐˜๐—ถ๐—น๐—ถ๐—ป๐—ด๐˜‚๐—ฎ๐—น ๐—–๐—ผ๐—ป๐˜ƒ๐—ฒ๐—ฟ๐˜€๐—ฎ๐˜๐—ถ๐—ผ๐—ป๐˜€
The agent supports both English and Hindi through a language-selection flow.

The user chooses the preferred language before starting the conversation. The selected language is then carried through the agent session.

For Hindi conversations, the agent is instructed to use "๐——๐—ฒ๐˜ƒ๐—ฎ๐—ป๐—ฎ๐—ด๐—ฎ๐—ฟ๐—ถ ๐˜€๐—ฐ๐—ฟ๐—ถ๐—ฝ๐˜" rather than randomly switching to Romanized Hindi.

๐Ÿฑ.๐—–๐—ฎ๐—น๐—น ๐—”๐—ป๐—ฎ๐—น๐˜†๐˜๐—ถ๐—ฐ๐˜€
I built a Call Analytics Dashboard that records real call outcomes.

It tracks metrics such as:

  • Total calls
  • Successful calls
  • Failed calls
  • Call outcome trends

The success condition is based on actual conversation outcomes, such as successful health guidance or successful human escalation, rather than simply counting every completed call as successful.

This made the system measurable and helped me evaluate whether the agent was actually completing useful conversations.

๐Ÿฒ.๐—ฆ๐—ฐ๐—ต๐—ฒ๐—ฑ๐˜‚๐—น๐—ฒ๐—ฑ ๐—ฅ๐—ฒ๐—บ๐—ถ๐—ป๐—ฑ๐—ฒ๐—ฟ ๐—–๐—ฎ๐—น๐—น๐˜€

One of the major features I added was scheduled reminder calling.

Users can ask "Aarogya Sahayak" to schedule a reminder using natural language, for example:

"Remind me in 5 minutes to drink water."

The agent understands the requested time, handles timezone and AM/PM clarification when required, and creates a reminder with a unique reference ID.

The reminder is then stored and monitored by a background scheduler. When the scheduled time arrives, the system reuses the existing outbound calling infrastructure to place the reminder call.

A key reliability feature is the exactly-once mechanism, which prevents the same reminder from being triggered more than once.

Users can also check the status of a reminder using its reference ID and cancel a reminder while it is still pending.

This turned reminders from a simple notification concept into an actual scheduled voice-call workflow connected to the existing agent infrastructure.

๐Ÿณ.๐—ช๐—ฒ๐—น๐—น๐—ป๐—ฒ๐˜€๐˜€ ๐—ง๐—ถ๐—ฝ๐˜€

I also added a dedicated Wellness Tips section for users who want simple health and wellness information without starting a full voice conversation.

The section provides practical, general wellness tips across five areas:

  • Hydration
  • Sleep & Rest
  • Healthy Eating
  • Daily Activity
  • Stress & Relaxation

Each category contains short and easy-to-follow suggestions so users can quickly find relevant information.

The feature is intentionally focused on general wellness rather than diagnosis or treatment. A clear disclaimer reminds users that the information is not medical advice.

This gives users another way to interact with Aarogya Sahayak when they simply want quick wellness guidance.

๐Ÿ“. ๐‚๐ก๐š๐ฅ๐ฅ๐ž๐ง๐ ๐ž๐ฌ ๐š๐ง๐ ๐‡๐จ๐ฐ ๐ˆ ๐Ž๐ฏ๐ž๐ซ๐œ๐š๐ฆ๐ž ๐“๐ก๐ž๐ฆ

Building a voice agent over multiple days was not always straightforward. A few problems taught me more than the features themselves.

  • ๐—ž๐—ฒ๐—ฒ๐—ฝ๐—ถ๐—ป๐—ด ๐—”๐—ด๐—ฒ๐—ป๐˜ ๐—ฅ๐—ฒ๐˜€๐—ฝ๐—ผ๐—ป๐˜€๐—ถ๐—ฏ๐—ถ๐—น๐—ถ๐˜๐—ถ๐—ฒ๐˜€ ๐—ฆ๐—ฒ๐—ฝ๐—ฎ๐—ฟ๐—ฎ๐˜๐—ฒ Initially, it would have been easy to let one agent handle everything.

Instead, I separated responsibilities between the main health assistant and the Clinic & Appointment Specialist.

The main agent handles general health conversations and safety routing, while the specialist focuses only on clinic and appointment-related tasks.

This made the routing logic clearer and reduced the chance of the specialist answering questions outside its intended role.

  • ๐—–๐—ผ๐—ป๐˜๐—ฒ๐˜…๐˜ ๐——๐˜‚๐—ฟ๐—ถ๐—ป๐—ด ๐—›๐—ฎ๐—ป๐—ฑ๐—ผ๐—ณ๐—ณ๐˜€ Another challenge was making sure the specialist understood what the user had already asked.

I did not want the user to repeat the entire conversation after every handoff.

The solution was to transfer only the relevant context, including a short request summary and the user's latest request, instead of transferring the entire conversation.

The same principle is used when handing the conversation back to the main agent.

  • ๐—Ÿ๐—ฎ๐—ป๐—ด๐˜‚๐—ฎ๐—ด๐—ฒ ๐—–๐—ผ๐—ป๐˜€๐—ถ๐˜€๐˜๐—ฒ๐—ป๐—ฐ๐˜† Another issue appeared when the agent sometimes mixed English and Hindi or used Romanized Hindi.

I added an explicit language-selection flow and made the selected language part of the agent session context.

For Hindi, the instructions explicitly require "Devanagari script" and prevent the agent from switching back to Romanized Hindi.

  • ๐—ฆ๐—ฐ๐—ต๐—ฒ๐—ฑ๐˜‚๐—น๐—ฒ๐—ฑ ๐—ฅ๐—ฒ๐—บ๐—ถ๐—ป๐—ฑ๐—ฒ๐—ฟ ๐—–๐—ฎ๐—น๐—น๐˜€ Adding scheduled reminder calls introduced another engineering challenge.

The system needed to understand natural-language time requests such as "in 5 minutes" while handling timezone and AM/PM ambiguity safely.

Another important requirement was preventing the same reminder from triggering more than once. Since the scheduler checks for due reminders repeatedly, simply checking the reminder status was not enough.

I implemented an atomic claiming mechanism so that each reminder is claimed exactly once before the outbound call is triggered. Reminders then move through states such as pending, triggered, completed, failed, or cancelled.

I also reused the existing outbound calling system instead of creating a separate dialing implementation. This kept the reminder feature integrated with the project's existing calling infrastructure.

  • ๐—ง๐—ฒ๐˜€๐˜๐—ถ๐—ป๐—ด ๐˜„๐—ถ๐˜๐—ต ๐—Ÿ๐—ถ๐—บ๐—ถ๐˜๐—ฒ๐—ฑ ๐—Ÿ๐—Ÿ๐—  ๐—ค๐˜‚๐—ผ๐˜๐—ฎ Some behavioral tests depend on LiveKit hosted inference and could not always be executed because the available free inference quota was exhausted.

Instead of treating those failures as application failures, I separated deterministic tests from LLM-dependent tests.

The deterministic test suite, linting, formatting, type checking, and frontend build could still be verified locally.

This was an important lesson: an external service failure and an application bug are not necessarily the same thing.

๐Ÿ”. ๐‡๐จ๐ฐ ๐‘๐ž๐š๐๐ž๐ซ๐ฌ ๐‚๐š๐ง ๐๐ฎ๐ข๐ฅ๐ ๐š๐ง๐ ๐‘๐ฎ๐ง ๐ˆ๐ญ:

If you want to build a similar voice agent, the architecture can be broken into four main parts:

๐Ÿญ. ๐—ฆ๐—ฝ๐—ฒ๐—ฒ๐—ฐ๐—ต-๐˜๐—ผ-๐—ง๐—ฒ๐˜…๐˜ (๐—ฆ๐—ง๐—ง) ๐˜๐—ผ ๐˜‚๐—ป๐—ฑ๐—ฒ๐—ฟ๐˜€๐˜๐—ฎ๐—ป๐—ฑ ๐˜„๐—ต๐—ฎ๐˜ ๐˜๐—ต๐—ฒ ๐˜‚๐˜€๐—ฒ๐—ฟ ๐˜€๐—ฎ๐˜†๐˜€

๐Ÿฎ. ๐—Ÿ๐—Ÿ๐—  ๐˜๐—ผ ๐˜‚๐—ป๐—ฑ๐—ฒ๐—ฟ๐˜€๐˜๐—ฎ๐—ป๐—ฑ ๐˜๐—ต๐—ฒ ๐—ฟ๐—ฒ๐—พ๐˜‚๐—ฒ๐˜€๐˜ ๐—ฎ๐—ป๐—ฑ ๐—ฑ๐—ฒ๐—ฐ๐—ถ๐—ฑ๐—ฒ ๐˜„๐—ต๐—ฎ๐˜ ๐˜๐—ผ ๐—ฑ๐—ผ

๐Ÿฏ. ๐—ง๐—ฒ๐˜…๐˜-๐˜๐—ผ-๐—ฆ๐—ฝ๐—ฒ๐—ฒ๐—ฐ๐—ต (๐—ง๐—ง๐—ฆ) ๐˜๐—ผ ๐˜€๐—ฝ๐—ฒ๐—ฎ๐—ธ ๐˜๐—ต๐—ฒ ๐—ฟ๐—ฒ๐˜€๐—ฝ๐—ผ๐—ป๐˜€๐—ฒ

๐Ÿฐ. ๐—ฅ๐—ฒ๐—ฎ๐—น-๐˜๐—ถ๐—บ๐—ฒ ๐˜๐—ฟ๐—ฎ๐—ป๐˜€๐—ฝ๐—ผ๐—ฟ๐˜ ๐˜๐—ผ ๐—ฐ๐—ผ๐—ป๐—ป๐—ฒ๐—ฐ๐˜ ๐˜๐—ต๐—ฒ ๐˜‚๐˜€๐—ฒ๐—ฟ ๐—ฎ๐—ป๐—ฑ ๐—ฎ๐—ด๐—ฒ๐—ป๐˜ ๐—ฑ๐˜‚๐—ฟ๐—ถ๐—ป๐—ด ๐—ฎ ๐—น๐—ถ๐˜ƒ๐—ฒ ๐—ฐ๐—ผ๐—ป๐˜ƒ๐—ฒ๐—ฟ๐˜€๐—ฎ๐˜๐—ถ๐—ผ๐—ป

For Aarogya Sahayak, I used LiveKit for the real-time agent session and Murf Falcon for the voice experience.

  • ๐‚๐ฅ๐จ๐ง๐ž ๐ญ๐ก๐ž ๐๐ซ๐จ๐ฃ๐ž๐œ๐ญ Start by cloning the repository:

Bash:--
git clone https://github.com/codewithvishuuu/murf-livekit-starter.git
cd murf-livekit-starter

  • ๐—–๐—ผ๐—ป๐—ณ๐—ถ๐—ด๐˜‚๐—ฟ๐—ฒ ๐—”๐—ฃ๐—œ ๐—ž๐—ฒ๐˜†๐˜€ API keys should never be hardcoded into the source code or committed to GitHub.

Store them in the project's local environment file, such as .env.local, according to the variables required by the project.

  • ๐—™๐—ผ๐—ฟ ๐—ฒ๐˜…๐—ฎ๐—บ๐—ฝ๐—น๐—ฒ: GOOGLE_API_KEY=your_key_here

Use your actual keys only in your local environment.

Make sure .env.local is included in .gitignore and never publish the file containing real credentials.

  • ๐—ฆ๐˜๐—ฎ๐—ฟ๐˜ ๐˜๐—ต๐—ฒ ๐—Ÿ๐—ผ๐—ฐ๐—ฎ๐—น ๐—Ÿ๐—ถ๐˜ƒ๐—ฒ๐—ž๐—ถ๐˜ ๐—ฆ๐—ฒ๐—ฟ๐˜ƒ๐—ฒ๐—ฟ
    If you are running LiveKit locally, start the local LiveKit server first. The backend agent connects to this server for the real-time voice session.

  • ๐—™๐—ผ๐—ฟ ๐—ฒ๐˜…๐—ฎ๐—บ๐—ฝ๐—น๐—ฒ:
    cd backend
    uv run python src/agent.py dev

Then start the frontend...

  • ๐—ฆ๐˜๐—ฎ๐—ฟ๐˜ ๐˜๐—ต๐—ฒ ๐—•๐—ฎ๐—ฐ๐—ธ๐—ฒ๐—ป๐—ฑ ๐—”๐—ด๐—ฒ๐—ป๐˜
    cd backend
    uv run python src/agent.py dev

  • ๐—ฆ๐˜๐—ฎ๐—ฟ๐˜ ๐˜๐—ต๐—ฒ ๐—™๐—ฟ๐—ผ๐—ป๐˜๐—ฒ๐—ป๐—ฑ
    Then start the frontend using the project's frontend development command.

Open the local application in your browser and start a conversation.

๐“๐ž๐ฌ๐ญ๐ข๐ง๐  ๐ญ๐ก๐ž ๐‚๐จ๐ง๐ฏ๐ž๐ซ๐ฌ๐š๐ญ๐ข๐จ๐ง:

A simple test flow is:

  1. Start the application.

  2. Select English or Hindi.

  3. Ask a normal health or wellness question.

  4. Ask for a clinic appointment.

  5. Verify that the main agent announces the specialist handoff.

  6. Continue the appointment conversation with the specialist.

  7. Ask for a general wellness topic and verify the specialist can hand the conversation back.

  8. Test the Human Support flow and verify that a reference ID is generated.

  9. Check the Call Analytics Dashboard after completing calls.

  10. Schedule a reminder using a natural-language request, such as "Remind me in 5 minutes to drink water."

  11. Verify that a unique reminder reference ID is generated.

  12. Open the Scheduled Reminders page and check the reminder status.

  13. Create a pending reminder and verify that it can be cancelled.

  14. Leave a reminder active and verify that the scheduled outbound call is triggered at the requested time.

  15. Verify that the same reminder is not triggered more than once.

This type of testing helped me verify the actual user journey across voice conversations, specialist handoffs, human support, scheduled reminders, and call analytics instead of relying only on automated tests.

๐—บ๐—ฎ๐—ฟ๐—ธ๐—ฑ๐—ผ๐˜„๐—ป
๐Ÿ•. ๐–๐ก๐š๐ญ ๐ˆ ๐–๐จ๐ฎ๐ฅ๐ ๐ˆ๐ฆ๐ฉ๐ซ๐จ๐ฏ๐ž ๐๐ž๐ฑ๐ญ:

There are still several things I would like to improve.

  • ๐—•๐—ฒ๐˜๐˜๐—ฒ๐—ฟ ๐—”๐—ฝ๐—ฝ๐—ผ๐—ถ๐—ป๐˜๐—บ๐—ฒ๐—ป๐˜ ๐—œ๐—ป๐˜๐—ฒ๐—ด๐—ฟ๐—ฎ๐˜๐—ถ๐—ผ๐—ป
    The current specialist focuses on appointment guidance and preparation. A future version could integrate real clinic availability and appointment booking instead of only guiding the user through the process.

  • ๐— ๐—ผ๐—ฟ๐—ฒ ๐—Ÿ๐—ฎ๐—ป๐—ด๐˜‚๐—ฎ๐—ด๐—ฒ ๐—ฆ๐˜‚๐—ฝ๐—ฝ๐—ผ๐—ฟ๐˜
    The current language-selection flow focuses on English and Hindi. More Indian languages could be added while keeping the same strict native-script approach.

  • ๐—•๐—ฒ๐˜๐˜๐—ฒ๐—ฟ ๐—ข๐—ฏ๐˜€๐—ฒ๐—ฟ๐˜ƒ๐—ฎ๐—ฏ๐—ถ๐—น๐—ถ๐˜๐˜†
    The analytics dashboard could be expanded with more operational metrics such as latency, handoff rates, tool usage, and failure reasons.

  • ๐— ๐—ผ๐—ฟ๐—ฒ ๐—ฅ๐—ผ๐—ฏ๐˜‚๐˜€๐˜ ๐—ง๐—ฒ๐˜€๐˜๐—ถ๐—ป๐—ด
    I would also like to expand automated behavioral testing with more real-world conversation scenarios and improve testing around external inference-service failures.

  • ๐— ๐—ผ๐—ฟ๐—ฒ ๐—”๐—ฑ๐˜ƒ๐—ฎ๐—ป๐—ฐ๐—ฒ๐—ฑ ๐—ฅ๐—ฒ๐—บ๐—ถ๐—ป๐—ฑ๐—ฒ๐—ฟ ๐—ช๐—ผ๐—ฟ๐—ธ๐—ณ๐—น๐—ผ๐˜„๐˜€
    The current reminder system supports natural-language scheduling, status tracking, cancellation, and outbound reminder calls. A future version could support recurring reminders, richer scheduling options, user-configurable reminder preferences, and more advanced delivery controls.

  • ๐— ๐—ผ๐—ฟ๐—ฒ ๐—ฆ๐—ฝ๐—ฒ๐—ฐ๐—ถ๐—ฎ๐—น๐—ถ๐˜€๐˜ ๐—”๐—ด๐—ฒ๐—ป๐˜๐˜€
    The same architecture could support additional focused agents, such as a pharmacy information specialist or a health-services navigation specialist, while keeping the main agent responsible for routing.

๐Ÿ–. ๐‹๐ข๐ง๐ค๐ฌ ๐ญ๐จ ๐ญ๐ก๐ž ๐‚๐จ๐๐ž ๐š๐ง๐ ๐ƒ๐ž๐ฆ๐จ:

The project is open for others to explore and learn from.

๐—š๐—ถ๐˜๐—›๐˜‚๐—ฏ ๐—ฅ๐—ฒ๐—ฝ๐—ผ๐˜€๐—ถ๐˜๐—ผ๐—ฟ๐˜†:
https://github.com/codewithvishuuu/murf-livekit-starter

The repository contains the agent implementation, prompts, specialist handoff logic, scheduled reminder calls, tests, frontend, analytics, wellness tips, and support flows.

I also recommend looking at the project structure and tests if you are building your own voice agent. The tests were especially useful for checking routing, safety rules, handoffs, handbacks, language behavior, and privacy boundaries.


๐…๐ข๐ง๐š๐ฅ ๐“๐ก๐จ๐ฎ๐ ๐ก๐ญ๐ฌ:

Building Aarogya Sahayak over these 10 days taught me that a useful voice agent is much more than connecting an LLM to speech.

The difficult part is designing the system around the model: defining clear responsibilities, creating safety boundaries, routing conversations to the right agent, preserving context, protecting user information, and measuring whether the system actually works.

As the project evolved, I also learned how features such as scheduled reminder calls and accessible wellness guidance can extend a voice agent beyond a single conversation while still keeping safety and privacy at the center.

The biggest lesson I learned is that a good voice agent should know not only "how to answer", but also "when not to answer itself".

That is where tools, specialist agents, analytics, scheduled workflows, and human support become important.

I'm grateful to "Murf AI" for organizing the "10 Days of Voice Agents โ€” #VoiceForBharat Edition" and giving me the opportunity to build, test, break, fix, and improve a real voice-agent project.

I'm building voice agents using the fastest TTS API โ€” "Murf Falcon".

Have you experimented with real-time voice pipelines or LiveKitintegrations yet?๐Ÿ› ๏ธ Whatโ€™s the biggest latency hurdle youโ€™ve run into? Drop your thoughts in the comments below!๐Ÿ‘‡๐Ÿ’ฌ

๐™๐™๐™–๐™ฃ๐™  ๐™ฎ๐™ค๐™ช ๐™›๐™ค๐™ง ๐™ง๐™š๐™–๐™™๐™ž๐™ฃ๐™œ! ๐™๐™š๐™š๐™ก ๐™›๐™ง๐™š๐™š ๐™ฉ๐™ค ๐™ง๐™š๐™–๐™˜๐™ ๐™ค๐™ช๐™ฉ ๐™ค๐™ง ๐™˜๐™ค๐™ฃ๐™ฃ๐™š๐™˜๐™ฉ ๐™ค๐™ฃ ๐™‡๐™ž๐™ฃ๐™ ๐™š๐™™๐™„๐™ฃ / ๐™‚๐™ž๐™ฉ๐™ƒ๐™ช๐™—๐Ÿค
๐‘ฝ๐’Š๐’”๐’‰๐’‚๐’ ๐‘ฒ๐’–๐’Ž๐’‚๐’“๐Ÿ’–

Top comments (0)