Gemini Interactions API
+
+ The Gemini Interactions API is Google's stateful conversation endpoint. Unlike the
+ standard
+ generateContent/streamGenerateContent endpoints, Interactions
+ uses previous_interaction_id for server-side conversation state, flat
+ outputs[] instead of nested candidates[].content.parts[], and
+ typed SSE events with an event_type field inside each JSON payload.
+
Endpoint
+| Method | +Path | +Format | +
|---|---|---|
| POST | +/v1beta/interactions | +SSE (typed JSON events) | +
Quick Start
+Set up a minimal mock that responds to a Gemini Interactions request:
+ +import { LLMock } from "@copilotkit/aimock";
+
+const mock = new LLMock();
+mock.on({ userMessage: "hello" }, { content: "Hi there!" });
+await mock.listen(4010);
+
+// Client sends:
+// POST /v1beta/interactions
+// { model: "gemini-2.5-flash", input: "hello", stream: true }
+ Request Format
++ The Interactions API accepts several input shapes. aimock normalizes all of them into the + unified fixture-matching format. +
+ +String Input (Simple Prompt)
+{
+ "model": "gemini-2.5-flash",
+ "input": "What is the capital of France?",
+ "stream": true
+}
+ Turn[] Input (Multi-Turn)
+{
+ "model": "gemini-2.5-flash",
+ "input": [
+ { "role": "user", "parts": [{ "type": "text", "text": "Hello" }] },
+ { "role": "model", "parts": [{ "type": "text", "text": "Hi there!" }] },
+ { "role": "user", "parts": [{ "type": "text", "text": "Tell me a joke" }] }
+ ],
+ "stream": true
+}
+ Content[] with Function Result (Tool Response)
+{
+ "model": "gemini-2.5-flash",
+ "input": [
+ {
+ "role": "user",
+ "parts": [
+ { "type": "function_result", "name": "get_weather", "call_id": "call_abc123", "result": "72F sunny" }
+ ]
+ }
+ ],
+ "previous_interaction_id": "interaction_abc123",
+ "stream": true
+}
+ Stateful Chaining
+
+ The previous_interaction_id field links turns together on the server side.
+ Each response includes an interaction_id that the client passes as
+ previous_interaction_id in the next request, eliminating the need to resend
+ full conversation history.
+
Fixture Matching
+
+ Fixtures use the same match object as all other providers. The most common
+ matchers for Interactions are userMessage and sequenceIndex.
+
userMessage Matching
+const fixture = {
+ match: { userMessage: "hello" },
+ response: { content: "Hi from Gemini Interactions!" },
+};
+ sequenceIndex for Multi-Turn Chains
+
+ Since the Interactions API is stateful, multi-turn conversations are the primary use case.
+ Use sequenceIndex to match by turn position:
+
const fixtures = [
+ {
+ match: { sequenceIndex: 0 },
+ response: {
+ toolCalls: [{ name: "get_weather", arguments: { city: "NYC" } }]
+ },
+ },
+ {
+ match: { sequenceIndex: 1 },
+ response: { content: "The weather in NYC is 72F and sunny." },
+ },
+];
+
+const instance = await createServer(fixtures);
+
+// Turn 1: model calls get_weather tool
+// Turn 2: after tool result, model produces final text
+ SSE Event Format
+
+ Unlike standard Gemini SSE (bare data: chunks), the Interactions API uses
+ typed events. Each SSE line is a data: JSON object containing an
+ event_type field.
+
Event Types
+| Event Type | +Description | +
|---|---|
interaction.start |
+ Opening event with interaction_id and model metadata | +
content.start |
+ Marks beginning of an output part | +
content.delta |
+ Incremental text or function_call chunk | +
content.stop |
+ Marks completion of an output part | +
interaction.complete |
+ Final event with usage metadata and finish reason | +
Text Streaming Example
+data: {"event_type":"interaction.start","interaction":{"id":"int_abc123","status":"in_progress"},"event_id":"evt_1"}
+
+data: {"event_type":"content.start","index":0,"content":{"type":"text"},"event_id":"evt_2"}
+
+data: {"event_type":"content.delta","index":0,"delta":{"type":"text","text":"Hi "},"event_id":"evt_3"}
+
+data: {"event_type":"content.delta","index":0,"delta":{"type":"text","text":"there!"},"event_id":"evt_4"}
+
+data: {"event_type":"content.stop","index":0,"event_id":"evt_5"}
+
+data: {"event_type":"interaction.complete","interaction":{"id":"int_abc123","status":"completed","usage":{"total_input_tokens":5,"total_output_tokens":3,"total_tokens":8}},"event_id":"evt_6"}
+ Tool Call Streaming Example
+data: {"event_type":"interaction.start","interaction":{"id":"int_def456","status":"in_progress"},"event_id":"evt_1"}
+
+data: {"event_type":"content.start","index":0,"content":{"type":"function_call"},"event_id":"evt_2"}
+
+data: {"event_type":"content.delta","index":0,"delta":{"type":"function_call","id":"tc_abc123","name":"get_weather","arguments":{"city":"NYC"}},"event_id":"evt_3"}
+
+data: {"event_type":"content.stop","index":0,"event_id":"evt_4"}
+
+data: {"event_type":"interaction.complete","interaction":{"id":"int_def456","status":"requires_action","usage":{"total_input_tokens":8,"total_output_tokens":12,"total_tokens":20}},"event_id":"evt_5"}
+ Recording
+
+ To record real Gemini Interactions API traffic, use the gemini provider
+ settings (same base URL, same API key). The Interactions endpoint shares the Gemini
+ infrastructure:
+
import { LLMock } from "@copilotkit/aimock";
+
+const mock = new LLMock({
+ record: {
+ providers: {
+ gemini: "https://generativelanguage.googleapis.com",
+ },
+ },
+});
+await mock.listen(4010);
+
+ Unmatched requests to /v1beta/interactions are proxied to the real API, and
+ the response is recorded as a new fixture.
+
Integration with TanStack AI
+
+ TanStack AI provides a geminiTextInteractions() adapter for the Interactions
+ API. When your client uses this adapter, point it at your aimock instance and the same
+ fixtures will serve the responses. See the
+ TanStack AI docs for adapter
+ configuration.
+
Known Limitations
++ The Gemini Interactions API is currently in beta. Both the real API and + aimock's support for it are subject to change as the API stabilizes. +
+-
+
- + Beta API — event types and request shapes may shift between + releases. + +
- + Text output + function tools only — the current scope covers text + generation and function calling. + +
-
+ Built-in tools not supported — Google's built-in tools
+ (
google_search,code_execution) are not yet mocked. +
+ - + Non-text modalities not supported — image, audio, and video + inputs/outputs are not handled by this endpoint. + +