{"record":{"id":"80e97081495fae41","repo":"mastra-ai/mastra","slug":"fieldpath-must-be-a-non-negative-number-of-mill-80e970","errorCode":null,"errorMessage":"${fieldPath} must be a non-negative number of milliseconds or a duration string like \"5m\" or \"1hr\".","messagePattern":"(.+?) must be a non-negative number of milliseconds or a duration string like \"5m\" or \"1hr\"\\.","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"error","filePath":"packages/memory/src/processors/observational-memory/observational-memory.ts","lineNumber":194,"sourceCode":"\n  if (value === 'auto') {\n    return value;\n  }\n\n  if (typeof value === 'number') {\n    if (!Number.isFinite(value) || value < 0) {\n      throw new Error(`${fieldPath} must be a non-negative number of milliseconds or a duration string like \"5m\".`);\n    }\n    return value;\n  }\n\n  const trimmed = value.trim();\n  const match = trimmed.match(\n    /^(\\d+(?:\\.\\d+)?)\\s*(ms|msec|msecs|millisecond|milliseconds|s|sec|secs|second|seconds|m|min|mins|minute|minutes|h|hr|hrs|hour|hours)$/i,\n  );\n\n  if (!match) {\n    throw new Error(\n      `${fieldPath} must be a non-negative number of milliseconds or a duration string like \"5m\" or \"1hr\".`,\n    );\n  }\n\n  const rawAmount = match[1]!;\n  const rawUnit = match[2]!;\n  const amount = Number(rawAmount);\n  const unit = rawUnit.toLowerCase();\n\n  if (!Number.isFinite(amount) || amount < 0) {\n    throw new Error(`${fieldPath} must be a non-negative number of milliseconds or a duration string like \"5m\".`);\n  }\n\n  const multiplier =\n    unit === 'ms' || unit === 'msec' || unit === 'msecs' || unit === 'millisecond' || unit === 'milliseconds'\n      ? 1\n      : unit === 's' || unit === 'sec' || unit === 'secs' || unit === 'second' || unit === 'seconds'\n        ? 1_000","sourceCodeStart":176,"sourceCodeEnd":212,"githubUrl":"https://github.com/mastra-ai/mastra/blob/75dd419e613fe9c39f846ffc500716141b74fda6/packages/memory/src/processors/observational-memory/observational-memory.ts#L176-L212","documentation":"When a TTL option is given as a string, parseActivationTTL parses it against a strict duration regex (number + unit like ms/s/m/h). An unrecognized format throws. This ensures durations are well-formed before they are converted to milliseconds.","triggerScenarios":"Passing a string TTL that doesn't match the pattern: \"5min\" (min alone is fine, but \"5minutes \" with trailing text, \"every 5 minutes\", \"5 mts\", \"1 day\", \"\", or \"5m30s\" all fail).","commonSituations":"Copy-pasting human-readable durations from docs or product specs; env-var strings with whitespace/quotes; ISO-8601 durations (\"PT5M\") which are not supported.","solutions":["Use supported forms: \"90\", \"500ms\", \"5s\", \"5m\", \"30min\", \"2hr\", \"1h\"","Trim the string and strip surrounding quotes/whitespace from env vars before passing","Convert unsupported units yourself (e.g. days -> hours or milliseconds)"],"exampleFix":"// before\nnew ObservationalMemory({ model, activateAfterIdle: \"PT5M\" }) // ISO-8601 unsupported\n// after\nnew ObservationalMemory({ model, activateAfterIdle: \"5m\" });","handlingStrategy":"validation","validationCode":"const DURATION_RE = /^(\\d+(?:\\.\\d+)?)\\s*(ms|msec|msecs|millisecond|milliseconds|s|sec|secs|second|seconds|m|min|mins|minute|minutes|h|hr|hrs|hour|hours)$/i;\nif (typeof ttl === 'string' && !DURATION_RE.test(ttl.trim())) {\n  throw new Error(`Unsupported duration string: ${ttl}`);\n}","typeGuard":"function isDurationString(v: unknown): v is string {\n  return typeof v === 'string' &&\n    /^(\\d+(?:\\.\\d+)?)\\s*(ms|msec|msecs|millisecond|milliseconds|s|sec|secs|second|seconds|m|min|mins|minute|minutes|h|hr|hrs|hour|hours)$/i.test(v.trim());\n}","tryCatchPattern":"try {\n  const mem = new ObservationalMemory(config);\n} catch (err) {\n  if (err instanceof Error && err.message.includes('duration string')) {\n    config.activateAfterIdle = '5m';\n  } else throw err;\n}","preventionTips":["Use only documented unit spellings: ms, s, sec, m, min, hr, h, hours etc.","Never pass ISO-8601 durations (\"PT5M\") or compound strings (\"5m30s\")","Trim and unquote env-var strings before assigning duration options","Add a schema validator (zod) for config values with the duration regex"],"tags":["config","validation","duration","parsing"],"backgroundTag":"invalid-config-value","analyzedSha":"75dd419e613fe9c39f846ffc500716141b74fda6","analyzedAt":"2026-08-30T00:15:31.844Z","schemaVersion":2},"datasetVersion":"2026-08-30T03:17:51.788Z"}