{"record":{"id":"91763dea8b755438","repo":"github/copilot-sdk","slug":"parallel-expects-an-array-of-functions-not-prom","errorCode":null,"errorMessage":"parallel() expects an array of functions, not promises. Wrap each call: () => agent(...)","messagePattern":"parallel\\(\\) expects an array of functions, not promises\\. Wrap each call: \\(\\) => agent\\(\\.\\.\\.\\)","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"error","filePath":"nodejs/src/session.ts","lineNumber":178,"sourceCode":"    );\n}\n\nconst FACTORY_LOG_FLUSH_DELAY_MS = 10;\nconst MAX_FACTORY_FANOUT_ITEMS = 4096;\n\nfunction assertFactoryFanoutSize(kind: \"parallel\" | \"pipeline\", size: number): void {\n    if (size > MAX_FACTORY_FANOUT_ITEMS) {\n        throw new Error(\n            `${kind}() accepts at most ${MAX_FACTORY_FANOUT_ITEMS} items; got ${size}.`\n        );\n    }\n}\n\nasync function runFactoryParallel<TResult>(\n    thunks: Array<() => Promise<TResult> | TResult>\n): Promise<Array<TResult | null>> {\n    if (!Array.isArray(thunks)) {\n        throw new Error(\n            \"parallel() expects an array of functions, not promises. Wrap each call: () => agent(...)\"\n        );\n    }\n    assertFactoryFanoutSize(\"parallel\", thunks.length);\n    if (thunks.some((thunk) => typeof thunk !== \"function\")) {\n        throw new Error(\n            \"parallel() expects an array of functions, not promises. Wrap each call: () => agent(...)\"\n        );\n    }\n    return Promise.all(\n        thunks.map((thunk) =>\n            Promise.resolve()\n                .then(() => thunk())\n                .catch((error) => {\n                    // Cancellation and hard runtime failures must propagate out\n                    // of the combinator rather than be mapped to a successful\n                    // `null`; otherwise an aborted run, or one that hit a\n                    // resource ceiling or durable-state failure, could be","sourceCodeStart":160,"sourceCodeEnd":196,"githubUrl":"https://github.com/github/copilot-sdk/blob/cd8cf15dc3f9e762615790aaed0a771a0f392755/nodejs/src/session.ts#L160-L196","documentation":"parallel() requires an array of zero-argument functions (thunks) so it controls when each task starts. Passing an array whose elements are not functions is rejected up front. The message specifically calls out the most common mistake: passing already-started promises instead of thunks.","triggerScenarios":"Calling parallel() with a non-array value (e.g. undefined, a single promise), or with an array of promises/awaited results instead of () => ... wrappers.","commonSituations":"Migrating from Promise.all style code: tasks.map(task => task.run()) already starts the work and yields promises; accidentally spreading or forgetting the wrapper arrow around agent(...) calls.","solutions":["Pass an array of functions: parallel(() => agent(...), () => agent(...)).","Ensure the argument is an array, not a single promise or value.","If work is already started as promises, either keep Promise.all or convert to deferred thunks."],"exampleFix":"// before\nawait session.parallel(agent(taskA), agent(taskB));\n// after\nawait session.parallel([() => agent(taskA), () => agent(taskB)]);","handlingStrategy":"type-guard","validationCode":"if (!Array.isArray(tasks)) throw new TypeError('parallel() needs an array of thunks');","typeGuard":"const isThunks = <T>(v: unknown): v is Array<() => T | Promise<T>> => Array.isArray(v) && v.every((x) => typeof x === 'function');","tryCatchPattern":"try { await session.parallel(tasks); } catch (e) { if (String(e.message).includes('Wrap each call')) console.error('Pass () => fn(), not fn()'); else throw e; }","preventionTips":["Always annotate thunk arrays: Array<() => Promise<T>>.","Never call agent(...) while building the array.","Enable TypeScript strict mode so promise-vs-function mismatches surface at compile time."],"tags":["typescript","argument-type","parallel"],"backgroundTag":"invalid-argument-value","analyzedSha":"cd8cf15dc3f9e762615790aaed0a771a0f392755","analyzedAt":"2026-09-09T18:32:31.973Z","contentChangedAt":"2026-09-09T18:32:31.973Z","schemaVersion":2},"datasetVersion":"2026-09-17T15:17:12.973Z"}