Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 5 additions & 5 deletions .size-limit.json
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@
"README.md",
"LICENSE"
],
"limit": "129.46 kB",
"limit": "132 kB",
"brotli": false,
"gzip": false
},
Expand All @@ -33,21 +33,21 @@
"build/globals.js",
"build/deno.js"
],
"limit": "881.85 kB",
"limit": "885 kB",
"brotli": false,
"gzip": false
},
{
"name": "libdefs",
"path": "build/*.d.ts",
"limit": "45.68 kB",
"limit": "48 kB",
"brotli": false,
"gzip": false
},
{
"name": "vendor",
"path": "build/vendor-*.{cjs,d.ts}",
"limit": "835.65 kB",
"limit": "840 kB",
"brotli": false,
"gzip": false
},
Expand All @@ -66,7 +66,7 @@
"README.md",
"LICENSE"
],
"limit": "944.60 kB",
"limit": "950 kB",
"brotli": false,
"gzip": false
}
Expand Down
9 changes: 5 additions & 4 deletions build/cli.cjs
Original file line number Diff line number Diff line change
Expand Up @@ -63,7 +63,7 @@ var import_util = require("./util.cjs");
function transformMarkdown(buf) {
var _a2;
const out = [];
const tabRe = /^( +|\t)/;
const tabRe = /^( {4,}|\t)/;
const fenceRe = new RegExp("^(?<indent> {0,3})(?<fence>(`{3,20}|~{3,20}))(?:(?<js>js|javascript|ts|typescript)|(?<bash>sh|shell|bash)|.*)$");
let state = "root";
let prevEmpty = true;
Expand Down Expand Up @@ -103,18 +103,18 @@ function transformMarkdown(buf) {
state = "tab";
continue;
}
prevEmpty = line === "";
prevEmpty = line.trim() === "";
out.push("// " + line);
continue;
}
case "tab":
if (line === "") out.push("");
if (line.trim() === "") out.push("");
else if (tabRe.test(line)) out.push(line);
else {
out.push("// " + line);
state = "root";
}
prevEmpty = line === "";
prevEmpty = line.trim() === "";
break;
case "fence":
if (isEnd(line)) {
Expand Down Expand Up @@ -250,6 +250,7 @@ function runScript(script, scriptPath, tempPath) {
import_node_process2.default.once("exit", rmTemp);
yield import(import_node_url.default.pathToFileURL(scriptPath).toString());
} finally {
import_node_process2.default.off("exit", rmTemp);
rmTemp();
}
});
Expand Down
57 changes: 53 additions & 4 deletions build/core.cjs
Original file line number Diff line number Diff line change
Expand Up @@ -238,7 +238,7 @@ ${details}`;
static getCallerLocationFromString(stackString = "unknown") {
const lines = stackString.split(/^\s*(at\s)?/m).filter((s) => s == null ? void 0 : s.includes(":"));
const i = lines.findIndex((l) => l.includes("Proxy.set"));
const offset = i < 0 ? i : i + 2;
const offset = i < 0 ? lines.findIndex((l) => /:\d+/.test(l)) : i + 2;
return (lines.find((l) => l.includes("file://")) || lines[offset] || stackString).trim();
}
static getCallerLocation(err = new Error("zx error")) {
Expand Down Expand Up @@ -282,7 +282,8 @@ var formatters = {
retry(entry) {
const attempt = `Attempt: ${entry.attempt}${entry.total == Infinity ? "" : `/${entry.total}`}`;
const delay = entry.delay > 0 ? `; next in ${entry.delay}ms` : "";
return `${import_vendor_core.chalk.bgRed.white(" FAIL ")} ${attempt}${delay}
const reason = entry.exception instanceof Error ? ` \u2014 ${entry.exception.message.split("\n")[0]}` : "";
return `${import_vendor_core.chalk.bgRed.white(" FAIL ")} ${attempt}${delay}${reason}
`;
},
end() {
Expand Down Expand Up @@ -321,6 +322,7 @@ var RESERVED_WORDS = /* @__PURE__ */ new Set([
"EOF"
]);
function formatCmd(cmd) {
var _a;
if (cmd == void 0) return import_vendor_core.chalk.grey("undefined");
let q = "";
let out = "$ ";
Expand Down Expand Up @@ -380,7 +382,9 @@ function formatCmd(cmd) {
}
} else {
buf += c;
if (c === q) {
const backslashes = ((_a = buf.slice(0, -1).match(/\\+$/)) == null ? void 0 : _a[0].length) || 0;
const isEscaped = backslashes % 2 === 1;
if (c === q && !isEscaped) {
cap();
q = "";
}
Expand Down Expand Up @@ -753,6 +757,15 @@ var _ProcessPromise = class _ProcessPromise extends Promise {
json() {
return this.then((o) => o.json());
}
tryJson() {
return this.then((o) => o.tryJson());
}
jsonl() {
return this.then((o) => o.jsonl());
}
tryJsonl() {
return this.then((o) => o.tryJsonl());
}
text(encoding) {
return this.then((o) => o.text(encoding));
}
Expand Down Expand Up @@ -1029,7 +1042,43 @@ var _ProcessOutput = class _ProcessOutput extends Error {
return !this._dto.error && this.exitCode === 0;
}
json() {
return JSON.parse(this.stdall);
try {
return JSON.parse(this.stdall);
} catch (e) {
const preview = this.stdall.length > 200 ? this.stdall.slice(0, 200) + "..." : this.stdall;
const formatted = preview.replace(/\n/g, "\u21B5");
throw new SyntaxError(
`Failed to parse command output as JSON: ${formatted}`
);
}
}
tryJson() {
try {
return JSON.parse(this.stdall);
} catch (e) {
return void 0;
}
}
jsonl() {
return this.lines().filter((line) => line.trim().length > 0).map((line, idx) => {
try {
return JSON.parse(line);
} catch (e) {
const preview = line.length > 100 ? line.slice(0, 100) + "..." : line;
throw new SyntaxError(
`Failed to parse JSONL line ${idx + 1}: ${preview}`
);
}
});
}
tryJsonl() {
return this.lines().filter((line) => line.trim().length > 0).map((line) => {
try {
return JSON.parse(line);
} catch (e) {
return void 0;
}
});
}
buffer() {
return import_node_buffer.Buffer.from(this.stdall);
Expand Down
6 changes: 6 additions & 0 deletions build/core.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -136,6 +136,9 @@ export declare class ProcessPromise extends Promise<ProcessOutput> {
get [Symbol.toStringTag](): string;
[Symbol.toPrimitive](): string;
json<T = any>(): Promise<T>;
tryJson<T = any>(): Promise<T | undefined>;
jsonl<T = any>(): Promise<T[]>;
tryJsonl<T = any>(): Promise<(T | undefined)[]>;
text(encoding?: Encoding): Promise<string>;
lines(delimiter?: Options['delimiter']): Promise<string[]>;
buffer(): Promise<Buffer>;
Expand Down Expand Up @@ -189,6 +192,9 @@ export declare class ProcessOutput extends Error {
get [Symbol.toStringTag](): string;
get ok(): boolean;
json<T = any>(): T;
tryJson<T = any>(): T | undefined;
jsonl<T = any>(): T[];
tryJsonl<T = any>(): (T | undefined)[];
buffer(): Buffer;
blob(type?: string): Blob;
text(encoding?: Encoding): string;
Expand Down
11 changes: 8 additions & 3 deletions build/goods.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@ export declare const parseArgv: (args?: string[], opts?: ArgvOpts, defs?: Record
export declare function updateArgv(args?: string[], opts?: ArgvOpts): void;
export declare const argv: minimist.ParsedArgs;
export declare function sleep(duration: Duration): Promise<void>;
export declare const responseToReadable: (response: Response, rs: Readable) => Readable;
export declare function fetch(url: RequestInfo, init?: RequestInit): Promise<Response> & {
pipe: {
(dest: TemplateStringsArray, ...args: any[]): ProcessPromise;
Expand All @@ -29,8 +30,12 @@ export declare function question(query?: string, { choices, input, output, }?: {
output?: NodeJS.WriteStream;
}): Promise<string>;
export declare function stdin(stream?: Readable): Promise<string>;
export declare function retry<T>(count: number, callback: () => T): Promise<T>;
export declare function retry<T>(count: number, duration: Duration | Generator<number>, callback: () => T): Promise<T>;
export declare function expBackoff(max?: Duration, delay?: Duration): Generator<number, void, unknown>;
export interface RetryOptions {
delay?: Duration | Generator<number>;
shouldRetry?: (err: unknown, attempt: number) => boolean;
}
export declare function retry<T>(count: number, callback: (attempt: number, lastErr?: unknown) => T): Promise<T>;
export declare function retry<T>(count: number, durationOrOptions: Duration | Generator<number> | RetryOptions, callback: (attempt: number, lastErr?: unknown) => T): Promise<T>;
export declare function expBackoff(max?: Duration, delay?: Duration, jitter?: boolean | number): Generator<number, void, unknown>;
export declare function spinner<T>(callback: () => T): Promise<T>;
export declare function spinner<T>(title: string, callback: () => T): Promise<T>;
60 changes: 46 additions & 14 deletions build/index.cjs
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@ __export(index_exports, {
parseArgv: () => parseArgv,
question: () => question,
quiet: () => quiet,
responseToReadable: () => responseToReadable,
retry: () => retry,
sleep: () => sleep,
spinner: () => spinner,
Expand Down Expand Up @@ -108,8 +109,12 @@ var responseToReadable = (response, rs) => {
return rs;
}
rs._read = () => __async(null, null, function* () {
const result = yield reader.read();
rs.push(result.done ? null : import_node_buffer.Buffer.from(result.value));
try {
const result = yield reader.read();
rs.push(result.done ? null : import_node_buffer.Buffer.from(result.value));
} catch (err) {
rs.destroy(err);
}
});
return rs;
};
Expand All @@ -125,12 +130,15 @@ function fetch(url, init) {
})(dest, ...args) : dest;
p.then(
(r) => {
var _a;
return responseToReadable(r, rs).pipe((_a = _dest.run) == null ? void 0 : _a.call(_dest));
const destStream = typeof (_dest == null ? void 0 : _dest.run) === "function" ? _dest.run() : _dest;
return responseToReadable(r, rs).pipe(destStream);
},
(err) => {
var _a;
return (_a = _dest.abort) == null ? void 0 : _a.call(_dest, err);
if (typeof (_dest == null ? void 0 : _dest.abort) === "function") {
_dest.abort(err);
} else if (typeof (_dest == null ? void 0 : _dest.destroy) === "function") {
_dest.destroy(err);
}
}
);
return _dest;
Expand Down Expand Up @@ -191,21 +199,34 @@ function stdin() {
}
function retry(count, d, cb) {
return __async(this, null, function* () {
var _a, _b;
if (typeof d === "function") return retry(count, 0, d);
if (!cb) throw new import_core.Fail("Callback is required for retry");
let duration = 0;
let shouldRetry;
if (typeof d === "object" && d !== null && !("next" in d) && !Array.isArray(d)) {
const opts = d;
duration = (_a = opts.delay) != null ? _a : 0;
shouldRetry = opts.shouldRetry;
} else {
duration = d;
}
const total = count;
const gen = typeof d === "object" ? d : (function* (d2) {
while (true) yield d2;
})((0, import_util.parseDuration)(d));
const gen = typeof duration === "object" && "next" in duration ? duration : (function* (dur) {
while (true) yield dur;
})((0, import_util.parseDuration)(duration));
let attempt = 0;
let lastErr;
while (count-- > 0) {
attempt++;
try {
return yield cb();
return yield cb(attempt, lastErr);
} catch (err) {
lastErr = err;
const delay = gen.next().value;
if (shouldRetry && !shouldRetry(err, attempt)) {
throw err;
}
const delay = (_b = gen.next().value) != null ? _b : 0;
import_core.$.log({
kind: "retry",
total,
Expand All @@ -222,12 +243,19 @@ function retry(count, d, cb) {
throw lastErr;
});
}
function* expBackoff(max = "60s", delay = "100ms") {
function* expBackoff(max = "60s", delay = "100ms", jitter = false) {
const maxMs = (0, import_util.parseDuration)(max);
const randMs = (0, import_util.parseDuration)(delay);
const jitterFactor = typeof jitter === "number" ? Math.min(Math.max(jitter, 0), 1) : jitter ? 0.2 : 0;
let n = 0;
while (true) {
yield Math.min(randMs * __pow(2, n++), maxMs);
const base = Math.min(randMs * __pow(2, n++), maxMs);
if (jitterFactor > 0) {
const delta = base * jitterFactor * (Math.random() * 2 - 1);
yield Math.max(0, Math.min(Math.round(base + delta), maxMs));
} else {
yield base;
}
}
}
function spinner(title, callback) {
Expand All @@ -244,7 +272,10 @@ function spinner(title, callback) {
return yield callback();
} finally {
clearInterval(id);
stream.write(" ".repeat((import_node_process.default.stdout.columns || 1) - 1) + "\r");
const c = stream.columns || import_node_process.default.stderr.columns || 80;
stream.write(
" ".repeat(Math.max(c, (title ? String(title).length : 0) + 10)) + "\r"
);
}
}));
});
Expand Down Expand Up @@ -281,6 +312,7 @@ function quiet(promise) {
parseArgv,
question,
quiet,
responseToReadable,
retry,
sleep,
spinner,
Expand Down
2 changes: 2 additions & 0 deletions build/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@ const {
parseArgv,
question,
quiet,
responseToReadable,
retry,
sleep,
spinner,
Expand Down Expand Up @@ -69,6 +70,7 @@ export {
parseArgv,
question,
quiet,
responseToReadable,
retry,
sleep,
spinner,
Expand Down
Loading
Loading