mastra-ai/mastra · error · HTTPException

conversation_id and previous_response_id must reference the

Error message

conversation_id and previous_response_id must reference the same conversation thread when both are provided

What it means

resolveThreadExecutionContext enforces that when a request supplies both conversation_id and previous_response_id, the stored response identified by previous_response_id must live in the same thread as conversation_id. Mixing threads would corrupt conversation continuity, so the server rejects it with this 400 before executing the agent.

Source

Thrown at packages/server/src/server/handlers/responses.ts:178

 * If `previous_response_id` is present, the request continues on that stored thread.
 * Otherwise, the route only creates or reuses a thread when the caller asked to store
 * the response and the resolved agent actually has memory configured.
 */
async function resolveThreadExecutionContext({
  agent,
  store,
  conversationId,
  previousResponseTurnRecord,
  requestContext,
}: {
  agent: Agent<any, any, any, any>;
  store: boolean;
  conversationId?: string;
  previousResponseTurnRecord: ResponseTurnRecord | null;
  requestContext: RequestContext;
}): Promise<ThreadExecutionContext | null> {
  if (conversationId && previousResponseTurnRecord && previousResponseTurnRecord.thread.id !== conversationId) {
    throw new HTTPException(400, {
      message:
        'conversation_id and previous_response_id must reference the same conversation thread when both are provided',
    });
  }

  if (previousResponseTurnRecord) {
    return {
      threadId: previousResponseTurnRecord.thread.id,
      resourceId: previousResponseTurnRecord.thread.resourceId,
    };
  }

  const effectiveThreadId = getEffectiveThreadId(requestContext, undefined);
  const effectiveResourceId = getEffectiveResourceId(requestContext, undefined);

  if (!store && !conversationId && !effectiveThreadId) {
    return null;
  }

View on GitHub (pinned to 75dd419e61)

Solutions

  1. Align conversation_id with the thread that owns previous_response_id (drop one of the two, or look up the stored response's thread first)
  2. If starting a new conversation, omit previous_response_id and let the server create/resolve the thread from conversation_id alone
  3. Fix client state so conversation_id and previous_response_id are captured from the same request/response pair
  4. If IDs were hardcoded or copied from logs/environment, fetch fresh values from the API instead

Example fix

// before
await client.responses.create({ agent_id: 'a', conversation_id: 'thread-A', previous_response_id: 'resp-from-thread-B', input: 'hi' });
// after
await client.responses.create({ agent_id: 'a', previous_response_id: 'resp-from-thread-B', input: 'hi' }); // thread inferred from stored response
Defensive patterns

Strategy: validation

Validate before calling

if (conversationId && previousResponseId) {
  const rec = await getResponseTurnRecord(previousResponseId);
  if (rec && rec.thread.id !== conversationId) throw new Error('conversation_id and previous_response_id reference different threads');
}

Type guard

null

Try / catch

null

Prevention

When it happens

Trigger: POST /api/responses where body.conversation_id = 'thread-A' but the response referenced by body.previous_response_id was stored under 'thread-B' (e.g., resuming a response while pointing at a different conversation, or copying IDs across conversations/agents).

Common situations: Clients caching conversation_id from one session and previous_response_id from another; multi-tab UIs mixing state; replaying logged payloads with a changed conversation_id; passing a previous_response_id returned for a different agent/conversation.

Related errors


AI-assisted analysis of mastra-ai/mastra@75dd419e61 (2026-08-30). Data as JSON: /api/errors/1fdbff2a3e0a1f80. Report an issue: GitHub.