{"record":{"id":"ca32ee526d28c83c","repo":"jackwener/OpenCLI","slug":"must-be-an-integer","errorCode":null,"errorMessage":"must be an integer","messagePattern":"must be an integer","errorType":"validation","errorClass":"ArgumentError","httpStatus":null,"severity":"error","filePath":"clis/grok/export-all.js","lineNumber":16,"sourceCode":"import { cli, Strategy } from '@jackwener/opencli/registry';\nimport { ArgumentError, AuthRequiredError, EmptyResultError, TimeoutError } from '@jackwener/opencli/errors';\nimport fs from 'node:fs';\nimport {\n  normalizeConversationRows,\n  normalizeManifestRows,\n  requireBooleanEvaluateResult,\n  requireObjectEvaluateResult,\n} from './export-utils.js';\nimport { GROK_DOMAIN, GROK_URL } from './utils.js';\n\nfunction normalizeInteger(value, defaultValue, label, { min = 0, max = Number.MAX_SAFE_INTEGER } = {}) {\n  const raw = value ?? defaultValue;\n  const n = Number(raw);\n  if (!Number.isInteger(n)) {\n    throw new ArgumentError(label, `must be an integer`);\n  }\n  if (n < min) {\n    throw new ArgumentError(label, `must be >= ${min}`);\n  }\n  if (n > max) {\n    throw new ArgumentError(label, `must be <= ${max}`);\n  }\n  return n;\n}\n\nasync function waitRandom(page, minMs, maxMs) {\n  if (maxMs <= 0) return;\n  const span = Math.max(0, maxMs - minMs);\n  const ms = minMs + Math.floor(Math.random() * (span + 1));\n  if (ms > 0) await page.wait(ms / 1000);\n}\n\nfunction readManifest(manifestPath, { offset, limit }) {","sourceCodeStart":1,"sourceCodeEnd":34,"githubUrl":"https://github.com/jackwener/OpenCLI/blob/49907e53dc3ade5c223ff0c4c2c2785687cec4e6/clis/grok/export-all.js#L1-L34","documentation":"ArgumentError thrown by normalizeInteger when a numeric option (limit, offset, maxScrolls, pageScrolls, pageTimeoutMs, or delayMinMs) is not a whole number after Number() coercion. The library validates all pagination/timing flags upfront so scraping never starts with ambiguous input.","triggerScenarios":"Passing any non-integer value (e.g. '3.5', 'abc', '', NaN) to limit/offset/maxScrolls/pageScrolls/pageTimeoutMs/delayMinMs in clis/grok/export-all.js.","commonSituations":"CLI flags like --limit=1.5 or --offset=oops; environment variables with stray characters; JS callers passing strings like '10px' or undefined-derived NaN values.","solutions":["Pass whole numbers only: --limit 10 --offset 0","Quote-free numeric env vars without units or whitespace","Coerce with Math.floor/parseInt and validate in your wrapper before calling","Check that a default value being supplied is an integer"],"exampleFix":"// before\ncli.exportAll({ limit: '5.5' });\n// after\ncli.exportAll({ limit: Number.parseInt('5.5', 10) }); // 5","handlingStrategy":"validation","validationCode":"function assertInt(v, label) { const n = Number(v); if (!Number.isInteger(n)) throw new Error(`${label} must be an integer, got ${JSON.stringify(v)}`); return n; }","typeGuard":"const isInt = (v) => typeof v === 'number' && Number.isInteger(v);","tryCatchPattern":"try { await cli.exportAll(opts); } catch (e) { if (e.name === 'ArgumentError' && /integer/.test(e.message)) { console.error(`Bad numeric option: ${e.message}`); } else throw e; }","preventionTips":["Parse CLI/env values with Number.parseInt/parseFloat before passing","Strip units and whitespace from numeric env vars","Add pre-call validation of all numeric options","Favor documented defaults over hand-computed values"],"tags":["argument-validation","cli-input","type-error"],"backgroundTag":"invalid-argument-type","analyzedSha":"49907e53dc3ade5c223ff0c4c2c2785687cec4e6","analyzedAt":"2026-08-29T08:14:47.543Z","schemaVersion":2},"datasetVersion":"2026-08-29T12:17:43.993Z"}