{"record":{"id":"9a0dbea309bafc99","repo":"mastra-ai/mastra","slug":"experiment-has-target","errorCode":"EXPERIMENT_HAS_TARGET","errorMessage":"Experiment ${args.experimentId} has a target (${experiment.targetType} \"${experiment.targetId}\"); results are produced by Mastra, not ingested. Use runExperimentItem instead.","messagePattern":"Experiment (.+?) has a target \\((.+?) \"(.+?)\"\\); results are produced by Mastra, not ingested\\. Use runExperimentItem instead\\.","errorType":"error_code","errorClass":"MastraError","httpStatus":null,"severity":"error","filePath":"packages/core/src/datasets/dataset.ts","lineNumber":919,"sourceCode":"    attempt?: number;\n    input?: unknown;\n    output?: unknown;\n    groundTruth?: unknown;\n    error?: { message: string; stack?: string; code?: string } | null;\n    startedAt?: Date;\n    completedAt?: Date;\n    traceId?: string;\n    scores?: {\n      scorerId: string;\n      scorerName?: string;\n      score: number;\n      reason?: string;\n      metadata?: Record<string, unknown>;\n    }[];\n  }): Promise<ExperimentResult> {\n    const experiment = await this.#getOwnedExperiment(args.experimentId);\n    if (experiment.targetType !== null) {\n      throw new MastraError({\n        id: 'EXPERIMENT_HAS_TARGET',\n        text: `Experiment ${args.experimentId} has a target (${experiment.targetType} \"${experiment.targetId}\"); results are produced by Mastra, not ingested. Use runExperimentItem instead.`,\n        domain: 'STORAGE',\n        category: 'USER',\n      });\n    }\n    if (experiment.status === 'completed' || experiment.status === 'failed') {\n      throw new MastraError({\n        id: 'EXPERIMENT_ALREADY_FINALIZED',\n        text: `Experiment ${args.experimentId} is already ${experiment.status}; no further results can be submitted`,\n        domain: 'STORAGE',\n        category: 'USER',\n      });\n    }\n\n    const datasetsStore = await this.#getDatasetsStore();\n    const item = await datasetsStore.getItemById({\n      id: args.itemId,","sourceCodeStart":901,"sourceCodeEnd":937,"githubUrl":"https://github.com/mastra-ai/mastra/blob/75dd419e613fe9c39f846ffc500716141b74fda6/packages/core/src/datasets/dataset.ts#L901-L937","documentation":"submitExperimentResult ingests externally produced results and is only valid for targetless experiments (targetType null). If the experiment has a bound target, Mastra itself produces results via runExperimentItem, so external ingestion is rejected to prevent double/conflicting results.","triggerScenarios":"Calling dataset.submitExperimentResult({ experimentId, ... }) on an experiment created with targetType/targetId set (e.g. bound to an agent or tool).","commonSituations":"Pipelines that submit results for all experiments indiscriminately; a target was added to an experiment that previously accepted external results; copying ingestion code between targetless and targeted experiment flows.","solutions":["Check experiment.targetType; only call submitExperimentResult when it is null","Use runExperimentItem for experiments with targets and let Mastra produce the results","Create a separate targetless experiment if results genuinely come from outside Mastra"],"exampleFix":"// before\nawait dataset.submitExperimentResult({ experimentId: 'exp-1', itemId: 'item-1', ... }); // exp-1 targets agent\n// after\nif (exp.targetType === null) {\n  await dataset.submitExperimentResult({ ... });\n} else {\n  await dataset.runExperimentItem({ experimentId: 'exp-1', itemId: 'item-1' });\n}","handlingStrategy":"validation","validationCode":"const exp = await getExperimentById(experimentId);\nif (exp && exp.targetType !== null) throw new Error('Experiment has a target; use runExperimentItem');","typeGuard":"function isTargetless(exp) { return exp !== null && exp.targetType === null; }","tryCatchPattern":"try {\n  await dataset.submitExperimentResult(args);\n} catch (e) {\n  if (isMastraError(e) && e.id === 'EXPERIMENT_HAS_TARGET') {\n    await dataset.runExperimentItem({ experimentId: args.experimentId, itemId: args.itemId });\n  } else throw e;\n}","preventionTips":["Gate ingestion code paths on experiment.targetType === null","Keep targeted and targetless experiment flows in separate pipelines","Name experiment ids to encode mode, e.g. 'ext-' prefix for targetless"],"tags":["storage","experiments","api-misuse","user-error"],"backgroundTag":"wrong-api-for-experiment-mode","analyzedSha":"75dd419e613fe9c39f846ffc500716141b74fda6","analyzedAt":"2026-08-30T00:15:31.844Z","schemaVersion":2},"datasetVersion":"2026-08-30T03:17:51.788Z"}