> ## Documentation Index
> Fetch the complete documentation index at: https://docs.goguava.ai/llms.txt
> Use this file to discover all available pages before exploring further.

# Inbound Q&A

> Build an inbound agent that answers policy questions with RAG

In this example, we'll build an inbound voice agent for a fictional property insurance company.
Callers can ask any question about their policy and receive accurate answers sourced from a policy document.

## Define the Agent

`guava.Agent` is our starting point for building Guava agents. We'll start by creating one with some basic background details.

<CodeGroup>
  ```python Python theme={null}
  import guava

  agent = guava.Agent(
      organization="Harper Valley Property Insurance",
      purpose="Answer questions regarding property insurance policy until there are no more questions",
  )
  ```

  ```typescript TypeScript theme={null}
  import * as guava from "@guava-ai/guava-sdk";

  const agent = new guava.Agent({
    organization: "Harper Valley Property Insurance",
    purpose: "Answer questions regarding property insurance policy until there are no more questions",
  });
  ```
</CodeGroup>

<Note>
  Guava discourages long system prompts that try to cover every scenario. The `purpose` is intentionally short and designed to orient the agent.
</Note>

## Set up DocumentQA

Next, we initialize a `DocumentQA` instance with the policy document. `DocumentQA` is a built-in RAG that covers a lot of simple use cases. It's a fully pluggable component
and we expect many users will bring their own RAG system.

<CodeGroup>
  ```python Python theme={null}
  from guava.helpers.rag import DocumentQA
  from guava.examples.example_data import PROPERTY_INSURANCE_POLICY

  document_qa = DocumentQA(documents=PROPERTY_INSURANCE_POLICY)
  ```

  ```typescript TypeScript theme={null}
  import { DocumentQA } from "@guava-ai/guava-sdk/helpers";
  import { PROPERTY_INSURANCE_POLICY } from "@guava-ai/guava-sdk/example-data";

  const documentQA = new DocumentQA({
    documents: PROPERTY_INSURANCE_POLICY,
    namespace: "harper-valley-property-insurance",
  });
  ```
</CodeGroup>

## Handle questions with on\_question

Whenever the caller asks something the agent cannot answer from context alone, Guava invokes the `on_question` callback with the question in natural language. We forward it to `DocumentQA` and return the answer.

<CodeGroup>
  ```python Python theme={null}
  @agent.on_question
  def on_question(call: guava.Call, question: str) -> str:
      return document_qa.ask(question)
  ```

  ```typescript TypeScript theme={null}
  agent.onQuestion(async (call: guava.Call, question: string) => {
    return await documentQA.ask(question);
  });
  ```
</CodeGroup>

The agent remains fully responsive during the lookup — it continues listening and engaging with the caller while waiting for your response. You are not latency-constrained in your `on_question` implementation.

<Note>
  **Bring your own RAG.** The `on_question` callback receives a plain string and expects a plain string back — you can plug in any knowledge base, vector store, or model you prefer.
</Note>

## Start the agent

Finally, we attach the agent to a channel so that we can actually talk to it.

<CodeGroup>
  ```python Python theme={null}
  # Run this to attach your agent to a phone number. Call your agent's number to talk to it.
  agent.listen_phone(os.environ["GUAVA_AGENT_NUMBER"])

  # Run this to receive a WebRTC link where you can talk to your agent in the browser.
  agent.listen_webrtc()

  # Run this to talk to your agent using your local audio device.
  agent.call_local()

  # Run this to test your agent in a text-based chat session in the terminal (no audio required).
  agent.chat()
  ```

  ```typescript TypeScript theme={null}
  // Run this to attach your agent to a phone number. Call your agent's number to talk to it.
  agent.listenPhone(process.env.GUAVA_AGENT_NUMBER!);

  // Run this to receive a WebRTC link where you can talk to your agent in the browser.
  agent.listenWebrtc();

  // Run this to talk to your agent using your local audio device.
  agent.callLocal();

  // Run this to test your agent in a text-based chat session in the terminal (no audio required).
  agent.chat();
  ```
</CodeGroup>

<Note>
  **No web servers required.** Guava does not require a public web server to receive inbound calls. All Guava agents can be hosted behind firewalls and NATs.
</Note>

## Complete example

<CodeGroup>
  ```python Python theme={null}
  import logging
  import os
  import guava
  import argparse

  from guava.helpers.rag import DocumentQA
  from guava import logging_utils, Agent
  from guava.examples.example_data import PROPERTY_INSURANCE_POLICY

  logger = logging.getLogger("guava.examples.property_insurance")

  agent = Agent(
      organization="Harper Valley Property Insurance",
      purpose="Answer questions regarding property insurance policy until there are no more questions",
  )

  # This is a built-in knowledge base helper that we will use for this example.
  # You can use any RAG system you prefer.
  document_qa = DocumentQA(documents=PROPERTY_INSURANCE_POLICY)

  # When the Agent is asked a question that it cannot answer, it will invoke the on_question callback.
  @agent.on_question
  def on_question(call: guava.Call, question: str) -> str:
      # Forward the Agent's question to the knowledge base and return the answer.
      # You can plug in any knowledge base system you want here.
      answer = document_qa.ask(question)
      logger.info("RAG answer: %s", answer)
      return answer

  if __name__ == "__main__":
      logging_utils.configure_logging()

      # Every Agent can be attached to multiple resources.
      parser = argparse.ArgumentParser()
      group = parser.add_mutually_exclusive_group(required=True)
      group.add_argument("--phone", action="store_true", help="Listen for phone calls.")
      group.add_argument("--webrtc", action="store_true", help="Create on a WebRTC code.")
      group.add_argument("--local", action="store_true", help="Start a local call.")
      group.add_argument("--chat", action="store_true", help="Start a text-based chat session for testing.")
      args = parser.parse_args()

      if args.phone:
          agent.listen_phone(os.environ["GUAVA_AGENT_NUMBER"])
      elif args.webrtc:
          agent.listen_webrtc()
      elif args.chat:
          agent.chat()
      else:
          agent.call_local()
  ```

  ```typescript TypeScript theme={null}
  import * as guava from "@guava-ai/guava-sdk";
  import { DocumentQA } from "@guava-ai/guava-sdk/helpers";
  import { PROPERTY_INSURANCE_POLICY } from "@guava-ai/guava-sdk/example-data";

  const agent = new guava.Agent({
    organization: "Harper Valley Property Insurance",
    purpose: "Answer questions regarding property insurance policy until there are no more questions",
  });

  // This is a built-in knowledge base helper that we will use for this example.
  // You can use any RAG system you prefer.
  const documentQA = new DocumentQA({
    documents: PROPERTY_INSURANCE_POLICY,
    namespace: "harper-valley-property-insurance",
  });

  // When the Agent is asked a question that it cannot answer, it will invoke the on_question callback.
  agent.onQuestion(async (call: guava.Call, question: string) => {
    // Forward the Agent's question to the knowledge base and return the answer.
    // You can plug in any knowledge base system you want here.
    return await documentQA.ask(question);
  });

  const args = process.argv.slice(2);
  if (args.includes("--webrtc")) {
    agent.listenWebrtc();
  } else if (args.includes("--phone")) {
    agent.listenPhone(process.env.GUAVA_AGENT_NUMBER!);
  } else if (args.includes("--local")) {
    agent.callLocal();
  } else if (args.includes("--chat")) {
    agent.chat();
  } else {
    console.error("Usage: guava-example property-insurance --phone | --webrtc | --local | --chat");
    process.exit(1);
  }
  ```
</CodeGroup>


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.