{"record":{"id":"9346f202169fd064","repo":"facebook/flow","slug":"flow-option-must-be-all-or-detect","errorCode":null,"errorMessage":"flow option must be \"all\" or \"detect\"","messagePattern":"flow option must be \"all\" or \"detect\"","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"error","filePath":"packages/flow-parser/oxidized-src/index.js","lineNumber":40,"sourceCode":"import * as TransformRecordSyntax from './estree/TransformRecordSyntax';\nimport * as StripFlowTypesForBabel from './estree/StripFlowTypesForBabel';\nimport * as StripFlowTypes from './estree/StripFlowTypes';\n\nconst DEFAULTS: {flow: 'detect'} = {\n  flow: 'detect',\n};\n\nfunction getOptions(opts?: ParserOptions): ParserOptions {\n  // Always build a fresh object so we never mutate the caller's input.\n  // Repeated calls with the same `opts` reference must produce identical\n  // results — earlier versions wrote normalized fields back onto `opts`,\n  // poisoning subsequent calls.\n  const options: ParserOptions = {...DEFAULTS, ...(opts ?? {})};\n\n  // Default to detecting whether to parse Flow syntax by the presence\n  // of an @flow pragma.\n  if (options.flow !== 'all' && options.flow !== 'detect') {\n    throw new Error('flow option must be \"all\" or \"detect\"');\n  }\n\n  if (options.sourceType === 'unambiguous') {\n    // Clear source type so that it will be detected from the contents of the file\n    delete options.sourceType;\n  } else if (\n    options.sourceType != null &&\n    options.sourceType !== 'script' &&\n    options.sourceType !== 'module'\n  ) {\n    throw new Error(\n      'sourceType option must be \"script\", \"module\", or \"unambiguous\" if set',\n    );\n  }\n\n  if (options.enableExperimentalComponentSyntax == null) {\n    options.enableExperimentalComponentSyntax = true; // Enable by default\n  }","sourceCodeStart":22,"sourceCodeEnd":58,"githubUrl":"https://github.com/facebook/flow/blob/5c865861998a8ccb7dbc82b0c1f511e9ef60c3d9/packages/flow-parser/oxidized-src/index.js#L22-L58","documentation":"The oxidized flow-parser's getOptions validates that the `flow` option is exactly 'all' or 'detect' (after spreading defaults, so an unset value defaults to 'detect'). Unlike the older hermes-parser JS API, booleans and 'none' are not accepted, and any other value throws immediately before parsing.","triggerScenarios":"Calling parse(code, {flow: false}), {flow: true}, or {flow: 'none'} — options that hermes-parser/babel-lineage parsers accepted. Migration code passing legacy option shapes into flow-parser's parse() hits this on the first call.","commonSituations":"Migrating from hermes-parser or other parsers where flow syntax enablement was boolean or included 'none'; config normalization layers that pass through user-supplied strings unchecked.","solutions":["Use flow: 'all' to always parse Flow syntax, or 'detect' (default) to parse only files with an @flow pragma.","To get the old 'none' behavior, use 'detect' and remove/ignore the @flow pragma so the file parses as plain JS.","Normalize options at your API boundary: reject or coerce unknown `flow` values before they reach parse()."],"exampleFix":"// before\nparse(code, {flow: false}); // or {flow: 'none'}\n\n// after\nparse(code, {flow: 'detect'}); // and ensure the file has no @flow pragma","handlingStrategy":"validation","validationCode":"// Normalize before calling parse\nfunction normalizeFlowOption(value) {\n  if (value === true) return 'all';\n  if (value === false || value === 'none') return 'detect'; // ensure no @flow pragma for none-semantics\n  if (value === 'all' || value === 'detect') return value;\n  throw new TypeError(`flow option must be \"all\" or \"detect\", got ${JSON.stringify(value)}`);\n}","typeGuard":"function isFlowOption(v) {\n  return v === 'all' || v === 'detect';\n}","tryCatchPattern":null,"preventionTips":["Never forward booleans or 'none' to flow-parser's parse().","Whitelist options at your own API boundary so bad values fail with your message, not the parser's."],"tags":["flow","parser","options","validation","api-migration"],"backgroundTag":"invalid-enum-value","analyzedSha":"5c865861998a8ccb7dbc82b0c1f511e9ef60c3d9","analyzedAt":"2026-08-20T10:41:37.992Z","contentChangedAt":"2026-08-20T10:41:37.992Z","schemaVersion":2},"datasetVersion":"2026-09-23T08:17:48.524Z"}