{"record":{"id":"484c8579d7024990","repo":"jackwener/OpenCLI","slug":"label-must-be-a-positive-integer-484c85","errorCode":null,"errorMessage":"--${label} must be a positive integer.","messagePattern":"--(.+?) must be a positive integer\\.","errorType":"validation","errorClass":"ArgumentError","httpStatus":null,"severity":"error","filePath":"clis/discord-app/utils.js","lineNumber":104,"sourceCode":"        channel_id: channelId,\n        ...(threadId ? { thread_id: threadId } : {}),\n        url: buildDiscordChannelUrl({ guildId, channelId, threadId }),\n    };\n}\n\nexport function buildDiscordChannelUrl({ guildId, channelId, threadId }) {\n    if (!guildId || !channelId) {\n        throw new ArgumentError('Discord channel navigation requires both guild_id and channel_id.');\n    }\n    const base = `${DISCORD_ORIGIN}/channels/${encodeURIComponent(String(guildId))}/${encodeURIComponent(String(channelId))}`;\n    return threadId ? `${base}/${encodeURIComponent(String(threadId))}` : base;\n}\n\nexport function parsePositiveInt(value, fallback, label) {\n    if (value === undefined || value === null || value === '') return fallback;\n    const raw = String(value).trim();\n    if (!/^\\d+$/.test(raw)) {\n        throw new ArgumentError(`--${label} must be a positive integer.`);\n    }\n    const parsed = parseInt(raw, 10);\n    if (!Number.isFinite(parsed) || parsed <= 0) {\n        throw new ArgumentError(`--${label} must be a positive integer.`);\n    }\n    return parsed;\n}\n\nexport function hasDiscordChannelTarget(kwargs = {}) {\n    return Boolean(stringArg(kwargs.url) || stringArg(kwargs.guild) || stringArg(kwargs.channel));\n}\n\nexport function buildListChannelsScript() {\n    return `\n      (function __opencliDiscordListChannels() {\n        function parseRoute(raw) {\n          try {\n            var url = new URL(raw, 'https://discord.com');","sourceCodeStart":86,"sourceCodeEnd":122,"githubUrl":"https://github.com/jackwener/OpenCLI/blob/49907e53dc3ade5c223ff0c4c2c2785687cec4e6/clis/discord-app/utils.js#L86-L122","documentation":"parsePositiveInt validates numeric CLI options (timeout, count, limit). Values that are not pure digit strings fail the /^\\d+$/ test and throw ArgumentError '--<label> must be a positive integer.' The first throw site handles non-numeric input; undefined/null/empty string fall back to the default instead of throwing.","triggerScenarios":"Passing --limit abc, --count '10x', a negative like --limit -5, or a float like --count 2.5 to commands such as `discord-app threads --limit`, `discord-app thread-read --count`, or timeout flags.","commonSituations":"Copy-pasting values with units ('30s', '5m'); shells expanding values oddly; scripting with unquoted variables that inject multiple words; locale-formatted numbers with separators ('1,000').","solutions":["Pass only bare positive integer digits, e.g. --limit 30, --count 20","Quote shell variables and validate numeric input before interpolating into flags","Strip units/formatting in your wrapper script (parse '30s' to 30) before invoking the CLI","Omit the flag entirely to use the built-in default"],"exampleFix":"// before\nspawn('discord-app', ['threads', '--limit', limit || 'all'])\n// after\nconst n = Number.parseInt(limit, 10);\nif (!Number.isInteger(n) || n <= 0) throw new Error('limit must be a positive integer');\nspawn('discord-app', ['threads', '--limit', String(n)])","handlingStrategy":"validation","validationCode":"function toPositiveInt(value, label) {\n  const raw = String(value ?? '').trim();\n  if (!/^\\d+$/.test(raw) || parseInt(raw, 10) <= 0) {\n    throw new Error(`--${label} must be a positive integer`);\n  }\n  return parseInt(raw, 10);\n}","typeGuard":"function isPositiveInt(v) {\n  return typeof v === 'number' ? Number.isInteger(v) && v > 0 : /^\\d+$/.test(String(v).trim());\n}","tryCatchPattern":"try {\n  await discordAppThreads(page, { limit: rawLimit });\n} catch (err) {\n  if (String(err.message).includes('must be a positive integer')) {\n    console.error(`--limit got '${rawLimit}': pass bare digits like --limit 30.`);\n  } else throw err;\n}","preventionTips":["Pass bare digit strings without units or separators","Quote and validate shell variables before interpolation","Omit the flag to use defaults instead of passing 0 or blank values","Sanitize numeric config values in wrapper scripts"],"tags":["argument-validation","cli","input-validation"],"backgroundTag":"invalid-argument-type","analyzedSha":"49907e53dc3ade5c223ff0c4c2c2785687cec4e6","analyzedAt":"2026-08-29T08:14:47.543Z","schemaVersion":2},"datasetVersion":"2026-08-29T12:17:43.993Z"}