{"record":{"id":"831073d5c7f19f93","repo":"jackwener/OpenCLI","slug":"lichess-perf-is-required-e-g-blitz-bullet","errorCode":null,"errorMessage":"lichess perf is required (e.g. \"blitz\", \"bullet\", \"rapid\")","messagePattern":"lichess perf is required \\(e\\.g\\. \"blitz\", \"bullet\", \"rapid\"\\)","errorType":"validation","errorClass":"ArgumentError","httpStatus":null,"severity":"error","filePath":"clis/lichess/utils.js","lineNumber":36,"sourceCode":"    'chess960', 'crazyhouse', 'antichess', 'atomic', 'horde',\n    'kingOfTheHill', 'racingKings', 'threeCheck',\n]);\n\nexport function requireUsername(value) {\n    const raw = String(value ?? '').trim();\n    if (!raw) throw new ArgumentError('lichess username is required');\n    if (!USERNAME_PATTERN.test(raw)) {\n        throw new ArgumentError(\n            `lichess username \"${value}\" is not a valid handle`,\n            'Allowed: letters, digits, underscore, dash; length 2-30.',\n        );\n    }\n    return raw;\n}\n\nexport function requirePerf(value) {\n    const raw = String(value ?? '').trim();\n    if (!raw) throw new ArgumentError('lichess perf is required (e.g. \"blitz\", \"bullet\", \"rapid\")');\n    if (!LICHESS_PERFS.has(raw)) {\n        throw new ArgumentError(\n            `lichess perf \"${value}\" is not recognised`,\n            `Allowed values: ${[...LICHESS_PERFS].join(', ')}.`,\n        );\n    }\n    return raw;\n}\n\nexport function requireBoundedInt(value, defaultValue, maxValue, label = 'limit') {\n    const raw = value ?? defaultValue;\n    const n = typeof raw === 'number' ? raw : Number(raw);\n    if (!Number.isInteger(n) || n <= 0) {\n        throw new ArgumentError(`lichess ${label} must be a positive integer`);\n    }\n    if (n > maxValue) {\n        throw new ArgumentError(`lichess ${label} must be <= ${maxValue}`);\n    }","sourceCodeStart":18,"sourceCodeEnd":54,"githubUrl":"https://github.com/jackwener/OpenCLI/blob/49907e53dc3ade5c223ff0c4c2c2785687cec4e6/clis/lichess/utils.js#L18-L54","documentation":"This ArgumentError is thrown by `requirePerf` when the perf (rating category) argument is empty or missing. The library needs an explicit perf such as 'blitz', 'bullet', or 'rapid' to select the rating to show.","triggerScenarios":"Calling `perf()` (via `requirePerf`) with `undefined`, `null`, `''`, or a whitespace-only value for the perf parameter.","commonSituations":"Omitting the perf positional/flag on the CLI; a config value defaulting to empty; scripting with an unset variable; assuming a default perf exists when none does.","solutions":["Supply a valid perf name, e.g. 'blitz', 'bullet', 'rapid', 'classical'","Check the command's --help for the accepted perf list","Fix the empty config/env value feeding the argument","Default the value in your wrapper before calling, e.g. `perfArg ?? 'blitz'`"],"exampleFix":"// before\nawait perf('drnik', ''); // ArgumentError: lichess perf is required\n// after\nawait perf('drnik', process.env.PERF ?? 'blitz');","handlingStrategy":"validation","validationCode":"const PERFS = new Set(['ultraBullet','bullet','blitz','rapid','classical','correspondence','chess960','crazyhouse','antichess','atomic','horde','kingOfTheHill','racingKings','threeCheck']);\nfunction assertPerf(v) {\n  const s = String(v ?? '').trim();\n  if (!s) throw new TypeError('perf is required (e.g. \"blitz\", \"bullet\", \"rapid\")');\n  return s;\n}\nassertPerf(opts.perf);","typeGuard":"function hasPerf(v) {\n  return typeof v === 'string' && v.trim().length > 0;\n}","tryCatchPattern":"try {\n  await perf(userArg, perfArg);\n} catch (e) {\n  if (e instanceof ArgumentError && /perf is required/.test(e.message)) {\n    console.error('Usage: lichess perf <username> <perf>  e.g. lichess perf drnik blitz');\n    process.exitCode = 2;\n  } else throw e;\n}","preventionTips":["Always supply the perf argument explicitly; there is no implicit default","Provide a default in your wrapper (`perfArg ?? 'blitz'`) if appropriate","Check --help for the exact accepted perf values","Validate CLI flags before invoking the command"],"tags":["lichess","argument-validation","missing-argument"],"backgroundTag":"missing-required-argument","analyzedSha":"49907e53dc3ade5c223ff0c4c2c2785687cec4e6","analyzedAt":"2026-08-29T08:14:47.543Z","schemaVersion":2},"datasetVersion":"2026-08-29T12:17:43.993Z"}