{"record":{"id":"43f320982506e599","repo":"can1357/oh-my-pi","slug":"context-messages-must-be-an-array","errorCode":null,"errorMessage":"`context.messages` must be an array","messagePattern":"`context\\.messages` must be an array","errorType":"validation","errorClass":"AIError.ValidationError","httpStatus":null,"severity":"error","filePath":"packages/ai/src/providers/pi-native-server.ts","lineNumber":125,"sourceCode":"\n\tlet modelId: string | undefined;\n\tif (typeof obj.modelId === \"string\" && obj.modelId.length > 0) {\n\t\tmodelId = obj.modelId;\n\t} else if (typeof obj.model === \"string\" && obj.model.length > 0) {\n\t\tmodelId = obj.model;\n\t} else if (typeof obj.model === \"object\" && obj.model !== null) {\n\t\tconst m = obj.model as Record<string, unknown>;\n\t\tif (typeof m.id === \"string\" && m.id.length > 0) modelId = m.id;\n\t}\n\tif (!modelId) throw new AIError.ValidationError(\"Missing `modelId` (or `model.id`) field\");\n\n\tconst context = obj.context;\n\tif (typeof context !== \"object\" || context === null || Array.isArray(context)) {\n\t\tthrow new AIError.ValidationError(\"Missing `context` object\");\n\t}\n\tconst ctxObj = context as Record<string, unknown>;\n\tif (!Array.isArray(ctxObj.messages)) {\n\t\tthrow new AIError.ValidationError(\"`context.messages` must be an array\");\n\t}\n\tif (ctxObj.systemPrompt !== undefined && !Array.isArray(ctxObj.systemPrompt)) {\n\t\tthrow new AIError.ValidationError(\"`context.systemPrompt` must be an array of strings when present\");\n\t}\n\tif (ctxObj.tools !== undefined && !Array.isArray(ctxObj.tools)) {\n\t\tthrow new AIError.ValidationError(\"`context.tools` must be an array when present\");\n\t}\n\n\tconst options: SimpleStreamOptions = {};\n\tconst rawOpts = obj.options;\n\tif (typeof rawOpts === \"object\" && rawOpts !== null && !Array.isArray(rawOpts)) {\n\t\tconst optsBag = options as Record<string, unknown>;\n\t\tfor (const [k, v] of Object.entries(rawOpts)) {\n\t\t\tif (v === undefined || v === null) continue;\n\t\t\tif (!ALLOWED_OPTION_KEYS.has(k as keyof SimpleStreamOptions)) continue;\n\t\t\toptsBag[k] = v;\n\t\t}\n\t}","sourceCodeStart":107,"sourceCodeEnd":143,"githubUrl":"https://github.com/can1357/oh-my-pi/blob/969062200754ea02cfac922e5ebb8c608c079e15/packages/ai/src/providers/pi-native-server.ts#L107-L143","documentation":"After confirming `context` is a plain object, parseRequest requires `context.messages` to be an array. This is the mandatory core of the conversation payload; without a messages array the server cannot build a prompt. A missing, non-array, or null `messages` field raises this ValidationError.","triggerScenarios":"Sending `{\"model\":...,\"context\":{}}`, `context:{\"messages\":null}`, or `context:{\"messages\":\"hello\"}` to the pi-native server endpoint.","commonSituations":"Clients that serialize only the last message as a string; templates with a placeholder left unfilled; SDK misuse passing a single message object instead of an array.","solutions":["Set `context.messages` to an array of message objects","If sending a single message, wrap it: `messages:[{role:\"user\",content:...}]`","Validate the payload client-side before POSTing"],"exampleFix":"// before\n{\"context\":{\"messages\":{\"role\":\"user\",\"content\":\"hi\"}}}\n// after\n{\"context\":{\"messages\":[{\"role\":\"user\",\"content\":\"hi\"}]}}","handlingStrategy":"validation","validationCode":"if (!Array.isArray(body?.context?.messages)) throw new Error('context.messages must be an array');","typeGuard":"function hasMessagesArray(ctx: unknown): ctx is { messages: unknown[] } {\n  return typeof ctx === 'object' && ctx !== null && Array.isArray((ctx as { messages?: unknown }).messages);\n}","tryCatchPattern":"try { const req = parseRequest(body); } catch (e) { if (e instanceof AIError.ValidationError && String(e.message).includes('`context.messages`')) return respond400('context.messages must be an array'); throw e; }","preventionTips":["Type messages as Message[] (required) in your client request type","Wrap single messages in arrays at the boundary","Schema-validate outgoing payloads (zod/arktype)"],"tags":["validation","request-schema","messages"],"backgroundTag":"schema-validation-failed","analyzedSha":"969062200754ea02cfac922e5ebb8c608c079e15","analyzedAt":"2026-08-31T10:29:35.737Z","schemaVersion":2},"datasetVersion":"2026-08-31T14:17:45.589Z"}