mastra-ai/mastra · error · Error
Extractor metadataKeyPath "${keyPath}" contains an unsafe pa
Error message
Extractor metadataKeyPath "${keyPath}" contains an unsafe path segment. What it means
When observational memory applies extractors, each extractor's metadataKeyPath (a dot-delimited path into extracted-value metadata) is split into segments and validated against a set of unsafe path segments (e.g. prototype-pollution names like __proto__/constructor). A path containing such a segment is rejected to prevent unsafe property traversal.
Source
Thrown at packages/memory/src/processors/observational-memory/extracted-values.ts:80
}
export function mergeExtractionFailures(
...failureSets: Array<ExtractionFailure[] | undefined>
): ExtractionFailure[] | undefined {
const failures = failureSets.flatMap(set => set ?? []);
return failures.length > 0 ? failures : undefined;
}
const UNSAFE_METADATA_PATH_SEGMENTS = new Set(['__proto__', 'constructor', 'prototype']);
function getMetadataPathSegments(keyPath: string | false): string[] | undefined {
if (keyPath === false) {
return undefined;
}
const segments = keyPath.split('.').filter(Boolean);
if (segments.some(segment => UNSAFE_METADATA_PATH_SEGMENTS.has(segment))) {
throw new Error(`Extractor metadataKeyPath "${keyPath}" contains an unsafe path segment.`);
}
return segments.length > 0 ? segments : undefined;
}
function getValueAtPath(metadata: ExtractedValueMetadata | undefined, keyPath: string | false): unknown {
if (!metadata) {
return undefined;
}
const segments = getMetadataPathSegments(keyPath);
if (!segments) {
return undefined;
}
let current: unknown = metadata;
for (const segment of segments) {
if (!current || typeof current !== 'object' || Array.isArray(current)) {
return undefined;View on GitHub (pinned to 75dd419e61)
Solutions
- Change the metadataKeyPath to use only safe identifier segments (no __proto__, constructor, prototype, etc.)
- Sanitize/allowlist user-derived path segments before building the key path
- If you need to store such a key, encode or prefix it (e.g. 'data.constructor_name') so it no longer collides with unsafe segments
Example fix
// before
new Extractor({ name: 'profile', metadataKeyPath: 'user.__proto__.name', ... });
// after
new Extractor({ name: 'profile', metadataKeyPath: 'user.profile.name', ... }); Defensive patterns
Strategy: validation
Validate before calling
const UNSAFE = new Set(['__proto__', 'constructor', 'prototype']);
const isSafeKeyPath = (p: string) => p.split('.').filter(Boolean).every(s => !UNSAFE.has(s));
if (!isSafeKeyPath(extractorConfig.metadataKeyPath)) throw new Error('metadataKeyPath has an unsafe segment'); Try / catch
try {
registerExtractor(cfg);
} catch (err) {
if (err instanceof Error && err.message.includes('unsafe path segment')) {
console.error(`Rejecting extractor with unsafe metadataKeyPath: ${cfg.metadataKeyPath}`);
}
throw err;
} Prevention
- Allowlist metadataKeyPath segments against a safe identifier regex /^[A-Za-z_][A-Za-z0-9_]*$/
- Never build metadataKeyPath directly from raw user input
- Add a unit test covering prototype-pollution payloads for extractor configs
When it happens
Trigger: Configuring an Extractor whose metadataKeyPath includes a segment like "__proto__", "constructor", or another entry in UNSAFE_METADATA_PATH_SEGMENTS; building key paths dynamically from user input that contains such tokens.
Common situations: Dynamically deriving metadataKeyPath from user-supplied field names; typos or copy-paste introducing reserved segment names; security tooling flagging and then someone 'testing' with prototype-pollution payloads.
Related errors
- Refusing to pass unsafe argument to shell command: ${JSON.st
- Extractor name "${name}" must produce a non-empty slug.
- Extractor name "${name}" produced invalid slug "${slug}".
- Extractor name is required.
- Cookie password must be at least 32 characters for SSO. Set
AI-assisted analysis of mastra-ai/mastra@75dd419e61 (2026-08-30).
Data as JSON: /api/errors/29ec994e814093ad.
Report an issue: GitHub.