jackwener/OpenCLI · error · ArgumentError

semanticscholar ${label} cannot be empty

Error message

semanticscholar ${label} cannot be empty

What it means

requireString validates that a user-supplied string argument (label identifies which, e.g. 'query') is non-empty after trimming; it throws ArgumentError when the value is null, undefined, or whitespace. The library throws this early so an empty required parameter never reaches the API as a malformed request.

Source

Thrown at clis/semanticscholar/utils.js:29

export const S2_GRAPH_BASE = 'https://api.semanticscholar.org/graph/v1';
export const S2_REC_BASE = 'https://api.semanticscholar.org/recommendations/v1';
const UA = 'opencli-semanticscholar-adapter (+https://github.com/jackwener/opencli)';

// Semantic Scholar paperId: 40-char lowercase hex (SHA-ish).
const S2_PAPER_ID = /^[0-9a-f]{40}$/i;
// DOIs: anything starting with 10. after an optional `doi:` / `doi.org/` prefix.
const DOI_BARE = /^10\.\S+$/;
// arXiv ids: modern `YYMM.NNNNN` form or legacy `archive/YYMMNNN`.
const ARXIV_MODERN = /^\d{4}\.\d{4,5}(?:v\d+)?$/;
const ARXIV_LEGACY = /^[a-z-]+\/\d{7}(?:v\d+)?$/i;
// Other Semantic Scholar accepted prefixes that we pass through verbatim.
const PREFIXED = /^(ARXIV|MAG|ACL|PMID|PMCID|URL|CorpusId|DBLP):/i;

export function requireString(value, label) {
    const s = String(value ?? '').trim();
    if (!s) {
        throw new ArgumentError(`semanticscholar ${label} cannot be empty`);
    }
    return s;
}

export function requireBoundedInt(value, defaultValue, maxValue, label = 'limit') {
    const raw = value ?? defaultValue;
    const n = typeof raw === 'number' ? raw : Number(raw);
    if (!Number.isInteger(n) || n <= 0) {
        throw new ArgumentError(`semanticscholar ${label} must be a positive integer`);
    }
    if (n > maxValue) {
        throw new ArgumentError(`semanticscholar ${label} must be <= ${maxValue}`);
    }
    return n;
}

/**
 * Resolve a user-supplied paper reference to a Semantic Scholar paper id

View on GitHub (pinned to 49907e53dc)

Solutions

  1. Re-run the command and supply the required argument (e.g. the search query).
  2. In scripts, default or assert the variable before invoking: `[ -n "$QUERY" ] || { echo 'QUERY is empty'; exit 1; }`.
  3. If the value should be optional, pass a sensible non-empty default instead of an empty string.

Example fix

// before
const query = requireString(args.query, 'query'); // throws when args.query is ''
// after
guard: if (!args.query?.trim()) { print usage; exit; }
const query = requireString(args.query, 'query');
Defensive patterns

Strategy: validation

Validate before calling

const query = (process.argv[3] ?? '').trim();
if (!query) { console.error('usage: opencli semanticscholar search <query>'); process.exit(1); }

Type guard

function isNonEmptyString(v) { return typeof v === 'string' && v.trim().length > 0; }

Try / catch

try {
    await runSearch(args);
} catch (err) {
    if (err instanceof ArgumentError && /cannot be empty/.test(err.message)) {
        console.error(`Missing argument: ${err.message}. See --help.`);
        process.exit(2);
    }
    throw err;
}

Prevention

When it happens

Trigger: Calling a semanticscholar command without its required string argument, e.g. `opencli semanticscholar search` with no query, or passing an empty/whitespace-only string ('', ' '), or a variable that is undefined/null.

Common situations: Shell scripts where an interpolated variable is empty ($QUERY unset); copy-paste dropping the argument; CI pipelines with missing env vars feeding the CLI.

Understand the failure class

Background: "missing required argument" and "the following required arguments were not provided": what required-argument errors mean and how to fix them — this error's family across 20 libraries.

Related errors


AI-assisted analysis of jackwener/OpenCLI@49907e53dc (2026-08-29). Data as JSON: /api/errors/c334576ca5c8e0fa. Report an issue: GitHub.