jackwener/OpenCLI · error · CliError
INVALID_INPUT
INVALID_INPUT
Error message
INVALID_INPUT
What it means
parseTarget first rejects inputs whose authority component is malformed (EMPTY_AUTHORITY_RE) — e.g. URLs like 'https://:password@' or 'https://@host' with an empty/degenerate userinfo. Zhihu write commands only accept normal HTTPS Zhihu URLs, so any input matching that pattern throws CliError with code INVALID_INPUT plus an example of the expected form.
Source
Thrown at clis/zhihu/target.js:17
import { CliError } from '@jackwener/opencli/errors';
const USER_RE = /^user:([A-Za-z0-9_-]+)$/;
const QUESTION_RE = /^question:(\d+)$/;
const ANSWER_RE = /^answer:(\d+):(\d+)$/;
const ARTICLE_RE = /^article:(\d+)$/;
const USER_PATH_RE = /^\/people\/([A-Za-z0-9_-]+)\/?$/;
const QUESTION_PATH_RE = /^\/question\/(\d+)\/?$/;
const ANSWER_PATH_RE = /^\/question\/(\d+)\/answer\/(\d+)\/?$/;
const ARTICLE_PATH_RE = /^\/p\/(\d+)\/?$/;
const EMPTY_AUTHORITY_RE = /^https:\/\/(?::)?@/i;
function isAllowedZhihuUrl(url) {
return url.protocol === 'https:' && url.username === '' && url.password === '' && url.port === '';
}
export function parseTarget(input) {
const value = String(input).trim();
if (EMPTY_AUTHORITY_RE.test(value)) {
throw new CliError('INVALID_INPUT', 'Zhihu write commands require a normal HTTPS Zhihu URL without malformed authority', 'Example: https://www.zhihu.com/question/123456');
}
if (value.startsWith('answer:') && !ANSWER_RE.test(value)) {
throw new CliError('INVALID_INPUT', 'Invalid answer target, expected answer:<questionId>:<answerId>', 'Example: opencli zhihu like answer:123:456 --execute');
}
let match = value.match(USER_RE);
if (match) {
return { kind: 'user', slug: match[1], url: `https://www.zhihu.com/people/${match[1]}` };
}
match = value.match(QUESTION_RE);
if (match) {
return { kind: 'question', id: match[1], url: `https://www.zhihu.com/question/${match[1]}` };
}
match = value.match(ANSWER_RE);
if (match) {
return {
kind: 'answer',
questionId: match[1],
id: match[2],View on GitHub (pinned to 49907e53dc)
Solutions
- Pass a plain URL without any userinfo: https://www.zhihu.com/question/123456
- Remove '@' and credentials from the argument; use the CLI's auth mechanism instead
- Quote the argument in the shell to prevent '@' or variable expansion issues
Example fix
// before opencli zhihu like https://$USER@www.zhihu.com/answer/456 --execute // after opencli zhihu like https://www.zhihu.com/answer/456 --execute
Defensive patterns
Strategy: validation
Validate before calling
function isCleanZhihuUrl(s) {
try {
const u = new URL(String(s).trim());
return u.protocol === 'https:' && u.hostname.endsWith('zhihu.com') &&
u.username === '' && u.password === '';
} catch { return false; }
}
if (!isCleanZhihuUrl(target)) throw new Error('strip credentials from the URL'); Type guard
function hasNoUserinfo(u) {
return u instanceof URL && u.username === '' && u.password === '' && u.port === '';
} Try / catch
try {
const t = parseTarget(rawInput);
} catch (err) {
if (err.code === 'INVALID_INPUT') {
console.error('Bad target:', err.suggestion ?? err.message);
} else throw err;
} Prevention
- Never embed credentials in URLs; use the CLI's auth flow
- Quote shell arguments to avoid '@'/variable-expansion artifacts
- Pre-validate targets with the URL constructor before invoking commands
- Copy canonical https://www.zhihu.com/... links only
When it happens
Trigger: Passing a URL with an empty username or password segment in the authority, e.g. 'https://@www.zhihu.com/question/123' or 'https://:x@www.zhihu.com/...', to any zhihu write command target.
Common situations: Pasting credentials into the URL from a shell history or script template, shell variable interpolation leaving an empty '@' segment (e.g. 'https://$USER@www.zhihu.com' with USER unset), copy-paste artifacts.
Related errors
- youdao note url cannot be empty
- Zhihu ${label} pagination returned a malformed next URL
- UNSUPPORTED_TARGET
- INVALID_INPUT
- Unknown 12306 station telecode "${trimmed}"
AI-assisted analysis of jackwener/OpenCLI@49907e53dc (2026-08-29).
Data as JSON: /api/errors/365f7d58f87c3969.
Report an issue: GitHub.