# Brain connectors

> Answer phone calls with the LLM app you already have, while VoiceLayer runs the voice.

Source: https://docs.vlayers.ai/build/brain-connectors

Kind: How-to guide

## What you'll build

A voice agent whose answers come from your existing text agent: an OpenAI-compatible endpoint, a LangChain app or a self-hosted model. VoiceLayer runs speech-to-text, text-to-speech, turn-taking and the phone line. Your endpoint is the brain.

Writing the brain in code inside a VoiceLayer agent instead? See [Brains in the SDK](https://docs.vlayers.ai/developers/sdks/brains).

## Two modes

| Mode | How it reaches your model | Use it when |
|---|---|---|
| **Tunnel** | You run the one-container `vl-brain` daemon. It dials out to VoiceLayer (no inbound ports) and forwards each turn to your local endpoint. LiteLLM is built in to normalise any provider. | Your model is private: on your laptop, in your network. |
| **Direct** | VoiceLayer calls a public OpenAI-compatible URL you save as a connection, over HTTPS, with protection against requests to private networks. Your key is encrypted and sent only from VoiceLayer's servers. | Your endpoint is already public. |

## Prerequisites

- An endpoint that answers chat requests: OpenAI-compatible, or any provider LiteLLM supports.
- For tunnel mode: Docker on a machine that can reach your endpoint.

## Step 1: Create a connector

Open **Dashboard → Custom LLM** and add a connector. Tunnel mode gives you a `vl_conn_` token.

> **Warning:** The token is shown once. Copy it when you create the connector. If it leaks, rotate it from the connector's row; the old token stops working at once.

## Step 2: Run it, or point at your URL

**Tunnel:** run the daemon with your token. If your endpoint already speaks the OpenAI format, set `VL_NORMALIZE=off` to skip LiteLLM:

```bash
docker run --rm \
  -e VL_CONNECTOR_TOKEN=$VL_CONNECTOR_TOKEN \
  -e VL_BRAIN_URL=https://your-brain.example.com/v1 \
  -e VL_BRAIN_API_KEY=$VL_BRAIN_API_KEY \
  -e VL_BRAIN_MODEL=your-model \
  -e VL_NORMALIZE=off \
  ghcr.io/paradox1612/vl-brain
```

Not OpenAI-shaped? Mount a LiteLLM config (Anthropic, Bedrock, Vertex, Ollama or a LangChain app) and set the connector's default model to its `model_name`:

```yaml
# litellm.config.yaml: map the model VoiceLayer asks for to your provider
model_list:
  - model_name: brain
    litellm_params:
      model: anthropic/claude-sonnet-5-5
      api_key: os.environ/ANTHROPIC_API_KEY
```

**Direct:** save a connection holding your public URL and key, and pick it on the connector.

## Step 3: Use it like any agent

The connector appears in the **Agents** list and works like any agent: change speech-to-text or text-to-speech, add tools, set up transfers. The one difference: the LLM is your brain, so the model picker is locked.

## Test it

Talk to the agent in the **Playground**, no number needed. When it behaves, attach a number. See [Phone numbers](https://docs.vlayers.ai/build/numbers).

## Common problems

| Problem | Fix |
|---|---|
| A direct connector still uses the old URL | An agent keeps the connection's URL as it was when published. Change the URL, then publish the agent again. |
| Calls to an agent stop | Disabling a brain connector stops the calls of agents bound to it. Enable it again. |
| The token no longer works | It was rotated. Create or rotate a token and restart the daemon with it. |

## Next steps

- [Brains in the SDK](https://docs.vlayers.ai/developers/sdks/brains): Bring a brain in code instead of a connector.
- [Voice and turn-taking](https://docs.vlayers.ai/build/voice): Make it sound human.
