{"record":{"id":"89a7d8737dcd839c","repo":"jackwener/OpenCLI","slug":"label-must-be-a-positive-integer-received","errorCode":null,"errorMessage":"${label} must be a positive integer. Received: \"${String(raw)}\"","messagePattern":"(.+?) must be a positive integer\\. Received: \"(.+?)\"","errorType":"validation","errorClass":"InvalidArgumentError","httpStatus":null,"severity":"error","filePath":"src/commands/auth.ts","lineNumber":76,"sourceCode":"  now?: Date;\n}\n\ninterface AuthRefreshSiteState {\n  last_touched_at?: string;\n  last_attempt_at?: string;\n  last_status?: AuthRefreshStatus;\n}\n\ninterface AuthRefreshState {\n  version: number;\n  sites: Record<string, AuthRefreshSiteState>;\n}\n\nfunction parsePositiveInt(raw: string | number | undefined, label: string, fallback: number): number {\n  if (raw === undefined || raw === null || raw === '') return fallback;\n  const parsed = Number(raw);\n  if (!Number.isInteger(parsed) || parsed <= 0) {\n    throw new InvalidArgumentError(`${label} must be a positive integer. Received: \"${String(raw)}\"`);\n  }\n  return parsed;\n}\n\nfunction parseSiteFilter(raw: string | undefined): Set<string> | null {\n  if (!raw || !raw.trim()) return null;\n  const sites = raw.split(',').map(site => site.trim()).filter(Boolean);\n  return sites.length > 0 ? new Set(sites) : null;\n}\n\nfunction defaultAuthRefreshStatePath(): string {\n  return join(homedir(), '.opencli', 'auth-refresh.json');\n}\n\nfunction emptyAuthRefreshState(): AuthRefreshState {\n  return { version: AUTH_REFRESH_STATE_VERSION, sites: {} };\n}\n","sourceCodeStart":58,"sourceCodeEnd":94,"githubUrl":"https://github.com/jackwener/OpenCLI/blob/49907e53dc3ade5c223ff0c4c2c2785687cec4e6/src/commands/auth.ts#L58-L94","documentation":"parsePositiveInt validates numeric CLI options such as --concurrency and --timeout in the auth commands. Any value that is not a whole number greater than zero (or empty/undefined, which falls back to the default) raises this commander InvalidArgumentError. The label in the message identifies which option was invalid.","triggerScenarios":"opencli auth status --concurrency 0, --concurrency -3, --concurrency 2.5, --concurrency abc, or --timeout '10 ' (non-numeric); also passing floats or strings that Number() cannot parse to an integer.","commonSituations":"Typos like --concurrency 1o; shell scripts interpolating empty or garbage values into the flag; assuming 0 means 'unlimited'; copy-pasting decimal defaults like 1.5.","solutions":["Pass a whole number >= 1, e.g. --concurrency 4 --timeout 20.","Omit the flag entirely to use the built-in default (3/8 for quick, 20 for full mode).","Fix the variable/interpolation in scripts that generate the command."],"exampleFix":"// before\nopencli auth status --concurrency 0\n// after\nopencli auth status --concurrency 4","handlingStrategy":"validation","validationCode":"function isPositiveInt(v: unknown): v is number {\n  return Number.isInteger(v) && (v as number) > 0;\n}\nif (opts.concurrency !== undefined && !isPositiveInt(opts.concurrency)) {\n  throw new Error('--concurrency must be a positive integer');\n}","typeGuard":"const isPositiveInt = (v: unknown): v is number =>\n  typeof v === 'number' && Number.isInteger(v) && v > 0;","tryCatchPattern":"try {\n  await opencli.authStatus({ concurrency: opts.concurrency });\n} catch (e) {\n  if (/must be a positive integer/.test(e.message)) {\n    console.error(`Bad numeric option: ${e.message}. Omit the flag to use the default.`);\n  } else throw e;\n}","preventionTips":["Omit --concurrency/--timeout to use safe defaults.","Never pass 0, negatives, decimals, or unit-suffixed values to numeric flags.","Validate interpolated variables in scripts before composing the command."],"tags":["cli","argument-validation","commander"],"backgroundTag":"invalid-argument-value","analyzedSha":"49907e53dc3ade5c223ff0c4c2c2785687cec4e6","analyzedAt":"2026-08-29T08:14:47.543Z","schemaVersion":2},"datasetVersion":"2026-08-29T12:17:43.993Z"}