{"record":{"id":"654198364ff0badc","repo":"koala73/worldmonitor","slug":"name-requiredenv-must-be-an-array","errorCode":null,"errorMessage":"${name} requiredEnv must be an array","messagePattern":"(.+?) requiredEnv must be an array","errorType":"validation","errorClass":"Error","httpStatus":null,"severity":"error","filePath":"scripts/audit-railway-watch-paths.mjs","lineNumber":199,"sourceCode":"  }\n  if (hasOwn(entry, 'watchPatterns')) {\n    if (!Array.isArray(entry.watchPatterns)\n      || entry.watchPatterns.some((pattern) => typeof pattern !== 'string')) {\n      throw new Error(`${name} watchPatterns must be an array of strings`);\n    }\n  }\n  if (hasOwn(entry, 'cronSchedule')\n    && entry.cronSchedule !== null\n    && typeof entry.cronSchedule !== 'string') {\n    throw new Error(`${name} cronSchedule must be a string or null`);\n  }\n  if (hasOwn(entry, 'startCommand')\n    && (typeof entry.startCommand !== 'string' || entry.startCommand.trim().length === 0)) {\n    throw new Error(`${name} startCommand must be a non-empty string`);\n  }\n  if (hasOwn(entry, 'requiredEnv')) {\n    if (!Array.isArray(entry.requiredEnv)) {\n      throw new Error(`${name} requiredEnv must be an array`);\n    }\n    for (const requirement of entry.requiredEnv) {\n      const alternatives = Array.isArray(requirement) ? requirement : [requirement];\n      if (alternatives.length === 0) {\n        throw new Error(`${name} requiredEnv contains an empty any-of group`);\n      }\n      for (const variable of alternatives) {\n        if (typeof variable !== 'string' || !/^[A-Z][A-Z0-9_]*$/.test(variable)) {\n          throw new Error(`${name} has invalid requiredEnv name ${JSON.stringify(variable)}`);\n        }\n      }\n    }\n  }\n  return entry;\n}\n\nexport function managedRailwayServices(registry) {\n  if (!Array.isArray(registry)) {","sourceCodeStart":181,"sourceCodeEnd":217,"githubUrl":"https://github.com/koala73/worldmonitor/blob/7d06c8633d256c18e38133030bc3613976a96ec9/scripts/audit-railway-watch-paths.mjs#L181-L217","documentation":"The audit's registry validator requires `requiredEnv`, when present, to be an array whose elements are either environment-variable name strings or arrays of alternatives (any-of groups). A non-array value (string, object, null) fails this check and the script aborts rather than auditing with a malformed requirement list.","triggerScenarios":"Calling assertRegistryEntry with an entry where the `requiredEnv` property exists but its value is not an array — e.g. `requiredEnv: \"TOKEN\"`, `requiredEnv: { TOKEN: true }`, or `requiredEnv: null`.","commonSituations":"A registry author writes a single env var as a bare string instead of [\"TOKEN\"], a JSON/YAML merge tool replaces the array with an object, or a template emits `requiredEnv: null` when no variables are required instead of omitting the key.","solutions":["Change `requiredEnv` to an array in the entry named by the error, e.g. requiredEnv: [\"RAILWAY_TOKEN\"] or with any-of groups [[\"A\", \"B\"]].","If no env vars are required, delete the `requiredEnv` key entirely — validation only runs when the key is present (hasOwn).","Check any generator/merge code that produces the entry and ensure it emits an array, not a string or object.","Add a JSON-schema or CI check on the registry file to catch shape errors before the audit runs."],"exampleFix":"// before\n{ name: 'worker', requiredEnv: 'RAILWAY_TOKEN' }\n// after\n{ name: 'worker', requiredEnv: ['RAILWAY_TOKEN'] }","handlingStrategy":"validation","validationCode":"if (entry.requiredEnv !== undefined && !Array.isArray(entry.requiredEnv)) {\n  throw new Error(`${entry.name}: requiredEnv must be an array`);\n}","typeGuard":"const hasRequiredEnvArray = (e) => e.requiredEnv === undefined || Array.isArray(e.requiredEnv);","tryCatchPattern":"try {\n  assertRegistryEntry(name, entry);\n} catch (err) {\n  if (err.message.includes('requiredEnv must be an array')) {\n    console.error(`Entry ${name}: wrap requiredEnv in an array, e.g. ['VAR_NAME'].`);\n    process.exitCode = 1;\n  } else throw err;\n}","preventionTips":["Always express env requirements as arrays, even for a single variable: [\"TOKEN\"].","Omit requiredEnv entirely instead of using null when none are required.","Validate the registry file against a JSON schema (requiredEnv: array) in CI.","Use [[\"A\",\"B\"]] any-of groups deliberately and document the shape next to the registry."],"tags":["validation","config","nodejs"],"backgroundTag":"type-mismatch","analyzedSha":"7d06c8633d256c18e38133030bc3613976a96ec9","analyzedAt":"2026-09-15T16:44:39.439Z","contentChangedAt":"2026-09-15T16:44:39.439Z","schemaVersion":2},"datasetVersion":"2026-09-15T18:17:12.389Z"}