◉GEMINI LABJP
●ARGON — gemini-4-argon is generally available as of 10/13, aimed at complex coding, agents, math and science●DEEP RES — deep-research-pro-preview-12-2025 shuts down 10/23, 6 days left. Move to deep-research-preview-04-2026●NANO — gemini-nano-banana-2.1 is GA (10/06). gemini-3.1-flash-image is deprecated with no shutdown date yet●MCP — One write-up cut an 85,000-token tool result to 310 tokens by wrapping it in an ADK FunctionTool●FLASH — gemini-3.7-flash and 3.5-flash now route automatically to newer Flash models (10/08)●NEW — Stop Re-Reading Every Crash Report: Gre…●ARGON — gemini-4-argon is generally available as of 10/13, aimed at complex coding, agents, math and science●DEEP RES — deep-research-pro-preview-12-2025 shuts down 10/23, 6 days left. Move to deep-research-preview-04-2026●NANO — gemini-nano-banana-2.1 is GA (10/06). gemini-3.1-flash-image is deprecated with no shutdown date yet●MCP — One write-up cut an 85,000-token tool result to 310 tokens by wrapping it in an ADK FunctionTool●FLASH — gemini-3.7-flash and 3.5-flash now route automatically to newer Flash models (10/08)●NEW — Stop Re-Reading Every Crash Report: Gre…
Articles/API / SDK
◈ API / SDK/2026-04-04Intermediate

Building Voice Agents with Gemini Live API: A Basics

Learn how to build real-time voice agents using Gemini Live API. From setup to implementation examples, this guide covers everything you need to get started.

Gemini Live API6Voice AgentReal-time AudioGemini Flash LiveAPI Development

The launch of Gemini Live API has transformed how AI agents interact with users. Moving beyond traditional text-based exchanges, developers can now create natural voice conversations with minimal latency. This shift significantly improves user experience and opens new possibilities for voice-driven applications.

Understanding Gemini Live API

Gemini Live API leverages Gemini Flash Live, Google's latest lightweight model optimized for real-time voice interactions.

Key Features

  • Real-time Processing: Processes incoming audio instantly with minimal delay
  • Natural Conversation: Recognizes vocal emotion and tone for more human-like responses
  • Low Latency: Edge-optimized processing ensures fast response times
  • Multi-turn Dialogue: Maintains conversation context across multiple exchanges

Gemini Flash Live is purpose-built for real-time scenarios, making it more efficient than standard Gemini models for voice applications.

Getting Started

1. Obtaining Your API Key

To use Gemini Live API, you'll need a Google API key.

Visit Google AI Studio and follow these steps:

  1. Click "Get API Key"
  2. Create or select a project
  3. Click "Create API Key"
  4. Copy the generated key
export GEMINI_API_KEY="YOUR_GEMINI_API_KEY"

2. Setting Up Your Environment

Here's a Node.js setup example:

npm init -y
npm install google-generative-ai dotenv

Basic Implementation

Minimal Voice Agent

This example demonstrates a voice agent that captures microphone input and sends it to Gemini Live API:

const { GoogleGenerativeAI } = require('@google/generative-ai');
require('dotenv').config();
 
const apiKey = process.env.GEMINI_API_KEY;
const genAI = new GoogleGenerativeAI(apiKey);
 
async function createVoiceAgent() {
  const model = genAI.getGenerativeModel({
    model: 'gemini-2.0-flash-live'
  });
 
  const session = model.startSession({
    generationConfig: {
      temperature: 0.7,
      topK: 40,
      topP: 0.95
    }
  });
 
  console.log('Voice agent initialized. Start speaking...');
 
  const audioData = Buffer.from('your_audio_bytes');
 
  try {
    const response = await session.sendMessage({
      inlineData: {
        mimeType: 'audio/webm',
        data: audioData.toString('base64')
      }
    });
 
    console.log('Agent response:');
    console.log(response.response.text());
 
  } catch (error) {
    console.error('An error occurred:', error);
  }
 
  await session.end();
}
 
createVoiceAgent();

Web Application Implementation

Here's how to capture voice input in a browser and send it to Gemini Live API:

<!DOCTYPE html>
<html>
<body>
  <button id="startBtn">Start</button>
  <button id="stopBtn">Stop</button>
  <div id="response"></div>
 
  <script>
    let mediaRecorder;
    let audioChunks = [];
 
    document.getElementById('startBtn').addEventListener('click', async () => {
      const stream = await navigator.mediaDevices.getUserMedia({ audio: true });
      mediaRecorder = new MediaRecorder(stream);
 
      mediaRecorder.ondataavailable = (event) => {
        audioChunks.push(event.data);
      };
 
      mediaRecorder.onstop = async () => {
        const audioBlob = new Blob(audioChunks, { type: 'audio/webm' });
        await sendToGeminiAPI(audioBlob);
      };
 
      mediaRecorder.start();
    });
 
    document.getElementById('stopBtn').addEventListener('click', () => {
      mediaRecorder.stop();
    });
 
    async function sendToGeminiAPI(audioBlob) {
      const audioBase64 = await blobToBase64(audioBlob);
 
      const response = await fetch('/api/gemini-voice', {
        method: 'POST',
        headers: { 'Content-Type': 'application/json' },
        body: JSON.stringify({
          audio: audioBase64,
          mimeType: 'audio/webm'
        })
      });
 
      const data = await response.json();
      document.getElementById('response').innerText = data.reply;
    }
 
    function blobToBase64(blob) {
      return new Promise((resolve) => {
        const reader = new FileReader();
        reader.onloadend = () => {
          const base64 = reader.result.split(',')[1];
          resolve(base64);
        };
        reader.readAsDataURL(blob);
      });
    }
  </script>
</body>
</html>

Backend Implementation (Node.js + Express)

const express = require('express');
const { GoogleGenerativeAI } = require('@google/generative-ai');
require('dotenv').config();
 
const app = express();
app.use(express.json({ limit: '50mb' }));
 
const genAI = new GoogleGenerativeAI(process.env.GEMINI_API_KEY);
 
app.post('/api/gemini-voice', async (req, res) => {
  try {
    const { audio, mimeType } = req.body;
 
    const model = genAI.getGenerativeModel({
      model: 'gemini-2.0-flash-live'
    });
 
    const response = await model.generateContent({
      contents: [
        {
          role: 'user',
          parts: [
            {
              inlineData: {
                mimeType: mimeType,
                data: audio
              }
            }
          ]
        }
      ]
    });
 
    const reply = response.response.text();
    res.json({ reply });
 
  } catch (error) {
    console.error('Error:', error);
    res.status(500).json({ error: error.message });
  }
});
 
app.listen(3000, () => {
  console.log('Server running on port 3000');
});

Advanced Voice Agent Features

1. Multi-turn Conversation

Maintain session state across multiple exchanges:

const session = model.startSession();
 
const response1 = await session.sendMessage(message1);
const response2 = await session.sendMessage(message2);
 
await session.end();

2. Custom System Instructions

Control agent behavior with system prompts:

const model = genAI.getGenerativeModel({
  model: 'gemini-2.0-flash-live',
  systemInstruction: {
    parts: [
      {
        text: 'You are a helpful customer service agent.'
      }
    ]
  }
});

Building on the Dolice Labs apps as an indie developer, I found that with voice the silence matters more than cleverness. I return a quick acknowledgment while generating, reconnect immediately on a drop, and watch for the user starting to speak so I can interrupt my own playback — not talking over them is half of what makes it feel natural.

Wrapping up

Gemini Live API enables developers to create natural voice conversation experiences with AI agents. Start with the examples provided and customize them for your specific use case. With Gemini Flash Live's optimized performance and understanding of natural language, your users will enjoy seamless voice interactions.

Share

Thank You for Reading

Gemini Lab is ad-free, supported entirely by members like you. We publish practical guides daily with implementation code, benchmarks, and production-ready patterns. If you've found it useful, we'd love to have you on board.

  • ✦Copy-paste ready implementation code
  • ✦New advanced guides published daily
  • ✦$5/mo or $10 for lifetime access
View Membership →

If you found this article helpful, a small tip ($1.50) would mean a lot to us. Your support helps keep this site ad-free and covers server and hosting costs.

Related Articles

◈ API / SDK2026-10-16
The Day /models Returns 200 but generateContent Returns 403 — Decide Your Triage Order Before It Happens
A triage order for the case where listing models succeeds with 200 but generation fails with 403 permission_denied. Includes a small diagnostic script that checks key, project, and billing in turn, why you should not retry a 403, and how to assemble what support needs.
◈ API / SDK2026-10-14
When Your config Raises "Extra inputs are not permitted", Check the Spelling of Every Key
If a google-genai call fails with a pydantic ValidationError (extra_forbidden) the moment you pass a config, it is almost always a one-letter typo. Here is the output I reproduced, a small function that checks keys before the call, and how to tell why response.text came back as None.
◈ API / SDK2026-10-08
When a Deprecation Has No Shutdown Date: Re-Picking an Image Model on Three Conditions
gemini-nano-banana-2.1 went GA on October 6, and gemini-3.1-flash-image was deprecated with no shutdown date. Here is a table and a short script for choosing a replacement by resolution, reference images, and search grounding.