{"record":{"id":"d458e1dd38b071e4","repo":"mastra-ai/mastra","slug":"outputstream-phase-cannot-be-executed-directly-us","errorCode":null,"errorMessage":"outputStream phase cannot be executed directly. Use streaming instead.","messagePattern":"outputStream phase cannot be executed directly\\. Use streaming instead\\.","errorType":"validation","errorClass":"HTTPException","httpStatus":400,"severity":"error","filePath":"packages/server/src/server/handlers/processors.ts","lineNumber":470,"sourceCode":"          case 'outputStep':\n            if (!processor.processOutputStep) {\n              throw new HTTPException(400, { message: 'Processor does not support outputStep phase' });\n            }\n            result = await processor.processOutputStep({\n              ...baseContext,\n              systemMessages: [],\n              stepNumber: 0,\n              steps: [],\n              finishReason: 'stop',\n              toolCalls: [],\n              text: extractTextFromMessages(messages),\n              usage: { inputTokens: undefined, outputTokens: undefined, totalTokens: undefined },\n            });\n            break;\n\n          case 'outputStream':\n            // outputStream is for streaming chunks, not a simple execute\n            throw new HTTPException(400, {\n              message: 'outputStream phase cannot be executed directly. Use streaming instead.',\n            });\n\n          default:\n            throw new HTTPException(400, { message: `Unknown phase: ${phase}` });\n        }\n\n        // Process the result\n        let outputMessages = messages;\n        if (result) {\n          if (Array.isArray(result)) {\n            outputMessages = result;\n          } else if (result.get && result.get.all && typeof result.get.all.db === 'function') {\n            // It's a MessageList\n            outputMessages = result.get.all.db();\n          } else if (result.messages) {\n            outputMessages = result.messages;\n          }","sourceCodeStart":452,"sourceCodeEnd":488,"githubUrl":"https://github.com/mastra-ai/mastra/blob/75dd419e613fe9c39f846ffc500716141b74fda6/packages/server/src/server/handlers/processors.ts#L452-L488","documentation":"The outputStream phase is driven by streaming chunks during agent runs and has no request/response 'execute' form. The handler intentionally refuses direct execution of phase='outputStream' with HTTP 400, telling the caller to use the streaming endpoint instead.","triggerScenarios":"POSTing phase='outputStream' to the non-streaming processor execute endpoint in packages/server/src/server/handlers/processors.ts.","commonSituations":"Scripted phase enumeration including 'outputStream'; copying a streaming test to the plain execute endpoint; misunderstanding that outputStream is a chunk-callback hook, not an invokable transformation.","solutions":["Use the streaming processor endpoint (or a streaming agent run) to exercise outputStream behavior.","Test with 'output' or 'outputResult' phases for request/response validation.","Remove 'outputStream' from any hardcoded phase list sent to the execute endpoint."],"exampleFix":"// before\nexecuteProcessor(id, 'outputStream', ctx);\n// after\nstreamProcessor(id, ctx); // consumes the SSE/streaming route, which drives processOutputStream","handlingStrategy":"validation","validationCode":"const EXECUTABLE_PHASES = ['input','inputStep','output','outputResult','outputStep'] as const;\nif (!EXECUTABLE_PHASES.includes(phase as any)) {\n  throw new Error(`${phase} must run via the streaming endpoint`);\n}","typeGuard":null,"tryCatchPattern":"try {\n  await exec(id, phase, ctx);\n} catch (e) {\n  if (e instanceof HTTPException && e.status === 400 && e.message.includes('streaming')) {\n    return streamExec(id, ctx); // switch to SSE/streaming transport\n  }\n  throw e;\n}","preventionTips":["Exclude 'outputStream' and other streaming-only phases from execute-endpoint callers.","Use a streaming client to test processOutputStream behavior.","Keep phase enums in one shared constant used by both client and server."],"tags":["http-400","processors","streaming"],"backgroundTag":"phase-requires-streaming","analyzedSha":"75dd419e613fe9c39f846ffc500716141b74fda6","analyzedAt":"2026-08-30T00:15:31.844Z","schemaVersion":2},"datasetVersion":"2026-08-30T03:17:51.788Z"}