jackwener/OpenCLI · error · ArgumentError

Bilibili summary URL must be a bilibili.com or b23.tv URL

Error message

Bilibili summary URL must be a bilibili.com or b23.tv URL

What it means

If the input parses as a URL but its hostname is neither bilibili.com nor b23.tv (checked by BILIBILI_HOST_RE and B23_HOST_RE), readBvid rejects it with this ArgumentError. The library will only resolve ids from official Bilibili domains; arbitrary third-party URLs are not fetched, partly for safety and partly because the extraction logic would not apply.

Source

Thrown at clis/bilibili/summary.js:48

    let parsed = null;
    try {
        parsed = new URL(input);
    } catch {
        // Bare b23.tv short codes are accepted by the shared resolver.
    }
    if (parsed) {
        if (parsed.protocol !== 'https:' && parsed.protocol !== 'http:') {
            throw new ArgumentError('Bilibili summary URL must use http or https');
        }
        if (BILIBILI_HOST_RE.test(parsed.hostname)) {
            const match = parsed.pathname.match(/\/(?:video|bangumi\/play)\/(BV[A-Za-z0-9]+)/i);
            if (!match) {
                throw new ArgumentError('Bilibili summary URL must contain a BV video id');
            }
            return match[1];
        }
        if (!B23_HOST_RE.test(parsed.hostname)) {
            throw new ArgumentError('Bilibili summary URL must be a bilibili.com or b23.tv URL');
        }
    }
    try {
        return await resolveBvid(input);
    } catch (error) {
        throw new ArgumentError(`Cannot resolve Bilibili BV ID from input: ${input}`, error instanceof Error ? error.message : String(error));
    }
}

function requireOkPayload(payload, label) {
    if (!payload || typeof payload !== 'object' || Array.isArray(payload)) {
        throw new CommandExecutionError(`Bilibili ${label} API returned a malformed payload`);
    }
    if (payload.code !== 0) {
        const message = payload.message ?? 'unknown error';
        if (payload.code === -101 || payload.code === -403 || /登录|权限|forbidden|permission|login/i.test(String(message))) {
            throw new AuthRequiredError('bilibili.com', `Bilibili ${label} API requires login or permission: ${message} (${payload.code})`);
        }

View on GitHub (pinned to 49907e53dc)

Solutions

  1. Use the canonical URL on www.bilibili.com or the b23.tv short link.
  2. Or extract the BV ID yourself and pass the bare id.
  3. Fix domain typos — the check accepts any *.bilibili.com and *.b23.tv subdomain.

Example fix

// before
await summaryCommand('https://mirror.example.com/watch/BV1xx411c7mD');
// after
await summaryCommand('https://www.bilibili.com/video/BV1xx411c7mD');
Defensive patterns

Strategy: validation

Validate before calling

const u = new URL(input);
const ok = /(^|\.)bilibili\.com$/i.test(u.hostname) || /(^|\.)b23\.tv$/i.test(u.hostname);
if (!ok) throw new Error(`Host ${u.hostname} is not allowed; use bilibili.com or b23.tv`);

Type guard

function isBilibiliHostUrl(u) {
  try {
    const h = new URL(u).hostname;
    return /(^|\.)bilibili\.com$/i.test(h) || /(^|\.)b23\.tv$/i.test(h);
  } catch { return false; }
}

Try / catch

try {
  await summaryCommand(input);
} catch (e) {
  if (/bilibili\.com or b23\.tv URL/.test(e.message)) {
    const bvid = input.match(/BV[A-Za-z0-9]+/)?.[0];
    if (bvid) await summaryCommand(bvid);
    else throw e;
  } else throw e;
}

Prevention

When it happens

Trigger: Passing URLs from other sites that embed Bilibili players, e.g. `https://www.youtube.com/watch?v=...`, a mirror site, or a localhost dev URL like `http://localhost:3000/video/BV1xx411c7mD`.

Common situations: Grabbing a link from an aggregator or embedded player page; typos in the domain (bilibili.co, bilibili.tv are not matched); testing against a local mock server whose host isn't bilibili.com.

Related errors


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