{"record":{"id":"cdd2ce08515fdb34","repo":"gatsbyjs/gatsby","slug":"result-of-a-worker-should-be-an-object-type-of","errorCode":null,"errorMessage":"Result of a worker should be an object, type of \"${typeof result}\" was given","messagePattern":"Result of a worker should be an object, type of \"(.+?)\" was given","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"packages/gatsby/src/utils/jobs/manager.ts","lineNumber":306,"sourceCode":"      0\n    )\n    activityForJobsProgress.start()\n    activitiesForJobTypes.set(jobType, activityForJobsProgress)\n  } else {\n    activityForJobsProgress.total++\n  }\n\n  const deferred = pDefer<Record<string, unknown>>()\n  jobsInProcess.set(job.contentDigest, {\n    id: job.id,\n    deferred,\n  })\n\n  try {\n    const result = await runJob(job)\n    // this check is to keep our worker results consistent for cloud\n    if (result != null && !_.isPlainObject(result)) {\n      throw new Error(\n        `Result of a worker should be an object, type of \"${typeof result}\" was given`\n      )\n    }\n    deferred.resolve(result)\n  } catch (err) {\n    deferred.reject(new WorkerError(err))\n  } finally {\n    // when all jobs are done we end the activity\n    if (--activeJobs === 0) {\n      hasActiveJobs!.resolve()\n      activityForJobs!.end()\n      // eslint-disable-next-line require-atomic-updates\n      activityForJobs = null\n    }\n\n    activityForJobsProgress.tick()\n  }\n","sourceCodeStart":288,"sourceCodeEnd":324,"githubUrl":"https://github.com/gatsbyjs/gatsby/blob/8b06340921ffdf23125a365b9c9923690cb62ce6/packages/gatsby/src/utils/jobs/manager.ts#L288-L324","documentation":"After a job runs, the manager requires the worker result to be a plain object (or null) so it stays consistent for Gatsby Cloud serialization. Any other type (string, number, boolean, array, class instance) throws.","triggerScenarios":"A worker function returns a primitive (e.g. a URL string) or an array instead of a plain object.","commonSituations":"Plugin worker returning a string URL instead of { url }; returning an array of paths instead of { paths }; returning a class instance.","solutions":["Return a plain object from the worker: {} or { value }.","Wrap primitives: return { url } instead of url.","Convert arrays/instances to plain objects before returning."],"exampleFix":"// before: worker returns a string\nmodule.exports.PROCESS = async (job) => transform(job).url\n// after: return a plain object\nmodule.exports.PROCESS = async (job) => ({ url: transform(job).url })","handlingStrategy":"validation","validationCode":"const _ = require('lodash')\nfunction assertPlainObjectResult(result) {\n  if (result != null && !_.isPlainObject(result)) {\n    throw new Error(`Worker must return a plain object, got ${typeof result}`)\n  }\n}","typeGuard":"function isPlainObjectOrNull(v) { return v == null || _.isPlainObject(v) }","tryCatchPattern":null,"preventionTips":["Always return {} or { key: value } from worker functions.","Wrap primitive results in an object before returning.","Add a worker unit test asserting the result is a plain object."],"tags":["jobs","worker"],"backgroundTag":null,"analyzedSha":"8b06340921ffdf23125a365b9c9923690cb62ce6","analyzedAt":"2026-08-13T02:36:21.405Z","schemaVersion":2},"datasetVersion":"2026-08-13T04:17:16.726Z"}