{"record":{"id":"8d29e3a50e01a07d","repo":"mastra-ai/mastra","slug":"missing-message-source-for-message-message","errorCode":null,"errorMessage":"Missing message source for message ${message}","messagePattern":"Missing message source for message (.+?)","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"packages/core/src/agent/message-list/state/MessageStateManager.ts","lineNumber":66,"sourceCode":"        }\n        this.newResponseMessages.add(message);\n        this.newResponseMessagesPersisted.add(message);\n        // Handle case where a client-side tool response was added as user input\n        if (this.newUserMessages.has(message)) {\n          this.newUserMessages.delete(message);\n        }\n        break;\n      case 'input':\n      case 'user': // deprecated alias for input\n        this.newUserMessages.add(message);\n        this.newUserMessagesPersisted.add(message);\n        break;\n      case 'context':\n        this.userContextMessages.add(message);\n        this.userContextMessagesPersisted.add(message);\n        break;\n      default:\n        throw new Error(`Missing message source for message ${message}`);\n    }\n  }\n\n  /**\n   * Check if a message belongs to the memory source\n   */\n  isMemoryMessage(message: MastraDBMessage): boolean {\n    return this.memoryMessages.has(message);\n  }\n\n  /**\n   * Check if a message belongs to the input source\n   */\n  isUserMessage(message: MastraDBMessage): boolean {\n    return this.newUserMessages.has(message);\n  }\n\n  /**","sourceCodeStart":48,"sourceCodeEnd":84,"githubUrl":"https://github.com/mastra-ai/mastra/blob/75dd419e613fe9c39f846ffc500716141b74fda6/packages/core/src/agent/message-list/state/MessageStateManager.ts#L48-L84","documentation":"MessageStateManager.addToSource buckets each message into a source set ('memory', 'input', 'context', ...). If a message arrives with a source value outside the known switch cases, it throws 'Missing message source for message <message>'. This is an internal invariant violation indicating the message carried an unrecognized/undefined source tag.","triggerScenarios":"Calling MessageStateManager methods (via updateMessageMetadataByToolCallId, mergeToolResultIntoPart, stepStart, markResponseMessageBoundary, etc.) with a message whose source is undefined or an unsupported string — typically from a caller that constructed a MessageList entry without tagging its origin.","commonSituations":"Custom code adding messages to MessageList via internal APIs without passing messageSource; storage layers deserializing messages that lost their source metadata; version mismatches between packages that changed the MessageSource union.","solutions":["Always add messages through the public MessageList.add APIs with an explicit messageSource ('memory', 'input', 'context', or 'response').","Check the message printed in the error for a missing/misspelled source field and fix the producer.","Align package versions (@mastra/core and dependent packages) so MessageSource unions match.","If migrating stored messages, backfill the source metadata during deserialization."],"exampleFix":"// before\nstateManager.addToSource(msg, undefined as any);\n// after\nstateManager.addToSource(msg, 'input');","handlingStrategy":"type-guard","validationCode":"const VALID_SOURCES = ['memory', 'input', 'context', 'response'] as const;\nfunction assertMessageSource(src: string | undefined) {\n  if (!src || !(VALID_SOURCES as readonly string[]).includes(src)) {\n    throw new Error(`Message source must be one of ${VALID_SOURCES.join('|')}, got: ${src}`);\n  }\n}","typeGuard":"function hasMessageSource(m: unknown): m is { source: 'memory' | 'input' | 'context' | 'response' } {\n  return typeof m === 'object' && m !== null &&\n    ['memory', 'input', 'context', 'response'].includes((m as any).source);\n}","tryCatchPattern":"try {\n  messageList.add(msg, source);\n} catch (e) {\n  if (e instanceof Error && e.message.startsWith('Missing message source for message')) {\n    console.error('Message added without a recognized source; defaulting to input');\n    messageList.add(msg, 'input');\n  } else throw e;\n}","preventionTips":["Only add messages via public MessageList.add with an explicit messageSource argument.","Persist the source field with messages so deserialization doesn't drop it.","Keep @mastra/core versions aligned across packages to avoid MessageSource union drift."],"tags":["message-list","internal-state","invariant","agent"],"backgroundTag":"missing-message-source","analyzedSha":"75dd419e613fe9c39f846ffc500716141b74fda6","analyzedAt":"2026-08-30T00:15:31.844Z","schemaVersion":2},"datasetVersion":"2026-08-30T03:17:51.788Z"}