codex-plugin-doctor 1.56.0 → 1.57.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +2 -2
- package/dist/core/doctor-size.d.ts +5 -1
- package/dist/core/doctor-size.js +62 -3
- package/dist/run-cli.js +32 -2
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -480,9 +480,9 @@ jobs:
|
|
|
480
480
|
runs-on: ubuntu-latest
|
|
481
481
|
steps:
|
|
482
482
|
- uses: actions/checkout@v5
|
|
483
|
-
- uses: Esquetta/CodexPluginDoctor@v1.
|
|
483
|
+
- uses: Esquetta/CodexPluginDoctor@v1.57.0
|
|
484
484
|
with:
|
|
485
|
-
version: "1.
|
|
485
|
+
version: "1.57.0"
|
|
486
486
|
path: .
|
|
487
487
|
runtime: "true"
|
|
488
488
|
policy: codex-publish
|
|
@@ -10,7 +10,11 @@ export interface DoctorSizeReport {
|
|
|
10
10
|
sizeHuman: string;
|
|
11
11
|
}>;
|
|
12
12
|
warnings: string[];
|
|
13
|
+
npmPackSize?: number;
|
|
14
|
+
npmPackSizeHuman?: string;
|
|
13
15
|
}
|
|
14
|
-
export declare function buildDoctorSize(targetPath: string
|
|
16
|
+
export declare function buildDoctorSize(targetPath: string, options?: {
|
|
17
|
+
npmPack?: boolean;
|
|
18
|
+
}): Promise<DoctorSizeReport>;
|
|
15
19
|
export declare function renderDoctorSize(report: DoctorSizeReport): string;
|
|
16
20
|
export declare function renderDoctorSizeJson(report: DoctorSizeReport): string;
|
package/dist/core/doctor-size.js
CHANGED
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import { readdir, stat } from "node:fs/promises";
|
|
2
|
+
import { execFile } from "node:child_process";
|
|
2
3
|
import path from "node:path";
|
|
3
4
|
const skippedDirs = new Set([
|
|
4
5
|
"node_modules",
|
|
@@ -68,11 +69,62 @@ async function scanDirectory(rootPath, currentPath = rootPath) {
|
|
|
68
69
|
}
|
|
69
70
|
return { totalSize, fileCount, largeFiles };
|
|
70
71
|
}
|
|
71
|
-
export async function buildDoctorSize(targetPath) {
|
|
72
|
+
export async function buildDoctorSize(targetPath, options = {}) {
|
|
72
73
|
const resolvedPath = path.resolve(targetPath);
|
|
73
74
|
const { totalSize, fileCount, largeFiles } = await scanDirectory(resolvedPath);
|
|
74
75
|
const warnings = [];
|
|
75
76
|
let status = "pass";
|
|
77
|
+
let npmPackSize;
|
|
78
|
+
let npmPackSizeHuman;
|
|
79
|
+
if (options.npmPack) {
|
|
80
|
+
try {
|
|
81
|
+
const packOutput = await new Promise((resolve, reject) => {
|
|
82
|
+
execFile("npm", ["pack", "--dry-run"], { cwd: resolvedPath, timeout: 30000, shell: process.platform === "win32" }, (error, stdout, stderr) => {
|
|
83
|
+
if (error) {
|
|
84
|
+
reject(new Error(stderr.trim() || error.message));
|
|
85
|
+
return;
|
|
86
|
+
}
|
|
87
|
+
resolve(stdout);
|
|
88
|
+
});
|
|
89
|
+
});
|
|
90
|
+
const tarballLine = packOutput.split("\n").find((line) => line.includes("total files") || line.includes("package size"));
|
|
91
|
+
if (tarballLine) {
|
|
92
|
+
const totalMatch = tarballLine.match(/(\d[\d.]*)\s*([KMG]?B)/i);
|
|
93
|
+
if (totalMatch) {
|
|
94
|
+
const value = Number.parseFloat(totalMatch[1]);
|
|
95
|
+
const unit = totalMatch[2].toUpperCase();
|
|
96
|
+
switch (unit) {
|
|
97
|
+
case "KB":
|
|
98
|
+
npmPackSize = Math.round(value * 1024);
|
|
99
|
+
break;
|
|
100
|
+
case "MB":
|
|
101
|
+
npmPackSize = Math.round(value * 1024 * 1024);
|
|
102
|
+
break;
|
|
103
|
+
case "GB":
|
|
104
|
+
npmPackSize = Math.round(value * 1024 * 1024 * 1024);
|
|
105
|
+
break;
|
|
106
|
+
default:
|
|
107
|
+
npmPackSize = Math.round(value);
|
|
108
|
+
}
|
|
109
|
+
npmPackSizeHuman = formatSize(npmPackSize);
|
|
110
|
+
}
|
|
111
|
+
}
|
|
112
|
+
if (npmPackSize === undefined) {
|
|
113
|
+
warnings.push("Could not determine npm pack size from output.");
|
|
114
|
+
}
|
|
115
|
+
else {
|
|
116
|
+
const diffPercent = totalSize > 0
|
|
117
|
+
? Math.abs(Math.round(((npmPackSize - totalSize) / totalSize) * 100))
|
|
118
|
+
: 0;
|
|
119
|
+
if (diffPercent > 50 && npmPackSize > totalSize) {
|
|
120
|
+
warnings.push(`npm pack size (${npmPackSizeHuman}) differs from local size (${formatSize(totalSize)}) by ${diffPercent}%.`);
|
|
121
|
+
}
|
|
122
|
+
}
|
|
123
|
+
}
|
|
124
|
+
catch (error) {
|
|
125
|
+
warnings.push(`npm pack failed: ${error.message}`);
|
|
126
|
+
}
|
|
127
|
+
}
|
|
76
128
|
if (totalSize >= packageSizeFailThreshold) {
|
|
77
129
|
status = "fail";
|
|
78
130
|
warnings.push(`Package size (${formatSize(totalSize)}) exceeds ${formatSize(packageSizeFailThreshold)}.`);
|
|
@@ -94,7 +146,9 @@ export async function buildDoctorSize(targetPath) {
|
|
|
94
146
|
totalSizeHuman: formatSize(totalSize),
|
|
95
147
|
fileCount,
|
|
96
148
|
largeFiles: largeFiles.slice(0, 10),
|
|
97
|
-
warnings
|
|
149
|
+
warnings,
|
|
150
|
+
npmPackSize,
|
|
151
|
+
npmPackSizeHuman
|
|
98
152
|
};
|
|
99
153
|
}
|
|
100
154
|
export function renderDoctorSize(report) {
|
|
@@ -104,6 +158,7 @@ export function renderDoctorSize(report) {
|
|
|
104
158
|
`Path: ${report.targetPath}`,
|
|
105
159
|
`Status: ${report.status.toUpperCase()}`,
|
|
106
160
|
`Total size: ${report.totalSizeHuman} (${report.fileCount} files)`,
|
|
161
|
+
report.npmPackSizeHuman ? `npm pack size: ${report.npmPackSizeHuman}` : "",
|
|
107
162
|
""
|
|
108
163
|
];
|
|
109
164
|
if (report.warnings.length > 0) {
|
|
@@ -134,6 +189,10 @@ export function renderDoctorSizeJson(report) {
|
|
|
134
189
|
totalSizeHuman: report.totalSizeHuman,
|
|
135
190
|
fileCount: report.fileCount,
|
|
136
191
|
largeFiles: report.largeFiles,
|
|
137
|
-
warnings: report.warnings
|
|
192
|
+
warnings: report.warnings,
|
|
193
|
+
...(report.npmPackSize !== undefined ? {
|
|
194
|
+
npmPackSize: report.npmPackSize,
|
|
195
|
+
npmPackSizeHuman: report.npmPackSizeHuman
|
|
196
|
+
} : {})
|
|
138
197
|
}, null, 2);
|
|
139
198
|
}
|
package/dist/run-cli.js
CHANGED
|
@@ -169,7 +169,7 @@ function parseRemoteNetworkFlags(flags, runtime) {
|
|
|
169
169
|
return { allowNetwork, allowLocalNetwork, allowSessionLifecycle, requireRemoteReliability };
|
|
170
170
|
}
|
|
171
171
|
function printUsage(io) {
|
|
172
|
-
io.writeStderr("Usage: codex-plugin-doctor check <path|--installed> [filter] [--policy codex-publish|mcp-strict|security] [--compat] [--json|--markdown|--badge-json|--badge-markdown] [--output <path>] [--history <path>] [--runtime [--allow-network [--allow-local-network]]] [--sandbox docker] [--require-runtime-approval --runtime-approval-digest <digest>] [--verbose-runtime] [--explain] [--no-animations] [--ascii] [--changed-since <ref>]\n codex-plugin-doctor audit --installed [filter] [--policy codex-publish|mcp-strict|security] [--security] [--compat] [--json] [--output <path>] [--cache] [--changed]\n codex-plugin-doctor audit deps <path> [--policy codex-publish|mcp-strict|security] [--recommend] [--json|--sarif] [--output <path>]\n codex-plugin-doctor mcp <path> [--runtime [--allow-network [--allow-local-network]]] [--json] [--output <path>]\n codex-plugin-doctor security <path> [--policy security] [--json|--scorecard]\n codex-plugin-doctor compat <path> [--all|--client <client>] [--json] [--scorecard] [--output <path>] [--install-preview|--apply --backup]\n codex-plugin-doctor suppress add <path> [--fingerprint <sha256> --reason <text> --expires-at YYYY-MM-DD] [--config <path>] [--json]\n codex-plugin-doctor suppress list <path> [--config <path>] [--json]\n codex-plugin-doctor suppress remove <path> [--fingerprint <sha256>|--index <n>] [--config <path>] [--json]\n codex-plugin-doctor fix <path> (--dry-run|--interactive --backup|--apply --backup)\n codex-plugin-doctor history <history.jsonl> [--json] [--fail-on-regression]\n codex-plugin-doctor watch <path> [--runtime] [--json] [--output <path>] [--debounce-ms <ms>] [--max-iterations <n>] [--fail-fast] [--accumulate-json <path>]\n codex-plugin-doctor doctor [npm <package>|contract|corpus [--manifest <corpus.json>] [--json] [--output <path>]|corpus metrics --manifest <corpus.json> [--json|--markdown] [--output <path>] [--min-precision <0..1>] [--min-recall <0..1>] [--max-false-positive-rate <0..1>]|runtime-plan <path> [--sandbox docker] [--json|--markdown] [--output <path>]|runtime-policy <path> [--sandbox docker] [--json] [--output <path>]|review-bundle <path> --output <dir> --sign-key-env NAME [--json] [--allow-dirty] [--allow-untagged]|review-bundle verify <bundle-dir> --target <path> --sign-key-env NAME [--json] [--output <path>] [--failures-only]|review-bundle diff --before <dir> --after <dir> [--json]|attest <path> [--sign-key-env NAME]|attest verify <attestation.json> --target <path> --sign-key-env NAME|release-evidence <path> --sign-key-env NAME [--runtime [--allow-network [--allow-local-network]]] [--sandbox docker] [--allow-dirty] [--allow-untagged] [--require-runtime-approval --runtime-approval-digest <digest>]|release-evidence verify <evidence.json> --target <path> --sign-key-env NAME|release-evidence asset <path> --tag <tag> --output <evidence.json> --sign-key-env NAME [--runtime [--allow-network [--allow-local-network]]] [--sandbox docker] [--allow-dirty] [--allow-untagged] [--require-runtime-approval --runtime-approval-digest <digest>] [--upload]|mcp <path> [--runtime [--allow-network [--allow-local-network]]]|inspector <path>|diff --before <path> --after <path>|recommend <path>|trust <path>|perf <path> [--max-total-ms <ms>] [--max-stage-ms stage=ms]|export --bundle <path>|snapshot|clients|--json|--update-check]\n codex-plugin-doctor init [path] [--template skill-only|mcp-stdio|mcp-http|full-runtime]\n codex-plugin-doctor init-ci [path]\n codex-plugin-doctor init-git-hooks [path] [--force] [--json]\n codex-plugin-doctor init-git-hooks [path] --remove [--json]\n codex-plugin-doctor completion bash|zsh|fish\n codex-plugin-doctor config validate <path> [--json]\n codex-plugin-doctor release check <path> [--json] [--runtime [--allow-network [--allow-local-network]]] [--sandbox docker]\n codex-plugin-doctor self-test\n codex-plugin-doctor list --installed\n codex-plugin-doctor explain <finding-id>\n codex-plugin-doctor --version\n\nFirst run:\n codex-plugin-doctor doctor\n codex-plugin-doctor self-test\n codex-plugin-doctor init my-plugin\n codex-plugin-doctor check . --runtime --explain");
|
|
172
|
+
io.writeStderr("Usage: codex-plugin-doctor check <path|--installed> [filter] [--policy codex-publish|mcp-strict|security] [--compat] [--json|--markdown|--badge-json|--badge-markdown] [--output <path>] [--history <path>] [--runtime [--allow-network [--allow-local-network]]] [--sandbox docker] [--require-runtime-approval --runtime-approval-digest <digest>] [--verbose-runtime] [--explain] [--no-animations] [--ascii] [--changed-since <ref>] [--fail-on <rule-id>]\n codex-plugin-doctor audit --installed [filter] [--policy codex-publish|mcp-strict|security] [--security] [--compat] [--json] [--output <path>] [--cache] [--changed]\n codex-plugin-doctor audit deps <path> [--policy codex-publish|mcp-strict|security] [--recommend] [--json|--sarif] [--output <path>]\n codex-plugin-doctor mcp <path> [--runtime [--allow-network [--allow-local-network]]] [--json] [--output <path>]\n codex-plugin-doctor security <path> [--policy security] [--json|--scorecard]\n codex-plugin-doctor compat <path> [--all|--client <client>] [--json] [--scorecard] [--output <path>] [--install-preview|--apply --backup]\n codex-plugin-doctor suppress add <path> [--fingerprint <sha256> --reason <text> --expires-at YYYY-MM-DD] [--config <path>] [--json]\n codex-plugin-doctor suppress list <path> [--config <path>] [--json]\n codex-plugin-doctor suppress remove <path> [--fingerprint <sha256>|--index <n>] [--config <path>] [--json]\n codex-plugin-doctor fix <path> (--dry-run|--interactive --backup|--apply --backup)\n codex-plugin-doctor history <history.jsonl> [--json] [--fail-on-regression]\n codex-plugin-doctor watch <path> [--runtime] [--json] [--output <path>] [--debounce-ms <ms>] [--max-iterations <n>] [--fail-fast] [--accumulate-json <path>]\n codex-plugin-doctor doctor [npm <package>|contract|corpus [--manifest <corpus.json>] [--json] [--output <path>]|corpus metrics --manifest <corpus.json> [--json|--markdown] [--output <path>] [--min-precision <0..1>] [--min-recall <0..1>] [--max-false-positive-rate <0..1>]|runtime-plan <path> [--sandbox docker] [--json|--markdown] [--output <path>]|runtime-policy <path> [--sandbox docker] [--json] [--output <path>]|review-bundle <path> --output <dir> --sign-key-env NAME [--json] [--allow-dirty] [--allow-untagged]|review-bundle verify <bundle-dir> --target <path> --sign-key-env NAME [--json] [--output <path>] [--failures-only]|review-bundle diff --before <dir> --after <dir> [--json]|attest <path> [--sign-key-env NAME]|attest verify <attestation.json> --target <path> --sign-key-env NAME|release-evidence <path> --sign-key-env NAME [--runtime [--allow-network [--allow-local-network]]] [--sandbox docker] [--allow-dirty] [--allow-untagged] [--require-runtime-approval --runtime-approval-digest <digest>]|release-evidence verify <evidence.json> --target <path> --sign-key-env NAME|release-evidence asset <path> --tag <tag> --output <evidence.json> --sign-key-env NAME [--runtime [--allow-network [--allow-local-network]]] [--sandbox docker] [--allow-dirty] [--allow-untagged] [--require-runtime-approval --runtime-approval-digest <digest>] [--upload]|mcp <path> [--runtime [--allow-network [--allow-local-network]]]|inspector <path>|diff --before <path> --after <path>|recommend <path>|trust <path>|perf <path> [--max-total-ms <ms>] [--max-stage-ms stage=ms]|export --bundle <path>|snapshot|clients|--json|--update-check]\n codex-plugin-doctor init [path] [--template skill-only|mcp-stdio|mcp-http|full-runtime]\n codex-plugin-doctor init-ci [path]\n codex-plugin-doctor init-git-hooks [path] [--force] [--json]\n codex-plugin-doctor init-git-hooks [path] --remove [--json]\n codex-plugin-doctor completion bash|zsh|fish\n codex-plugin-doctor config validate <path> [--json]\n codex-plugin-doctor release check <path> [--json] [--runtime [--allow-network [--allow-local-network]]] [--sandbox docker]\n codex-plugin-doctor self-test\n codex-plugin-doctor list --installed\n codex-plugin-doctor explain <finding-id>\n codex-plugin-doctor --version\n\nFirst run:\n codex-plugin-doctor doctor\n codex-plugin-doctor self-test\n codex-plugin-doctor init my-plugin\n codex-plugin-doctor check . --runtime --explain");
|
|
173
173
|
io.writeStderr("Registry readiness: codex-plugin-doctor registry check <server.json|directory> [--json] [--output <path>] [--require-registry-readiness]\n"
|
|
174
174
|
+ " codex-plugin-doctor registry inspect <server-name> --allow-network [--json] [--output <path>] [--require-registry-readiness]\n"
|
|
175
175
|
+ "Registry publication preflight: codex-plugin-doctor registry preflight <server.json|directory> [--allow-network] [--json] [--output <path>] [--require-publish-ready]");
|
|
@@ -2108,7 +2108,8 @@ export async function runCli(args, io = defaultIo, options = {}) {
|
|
|
2108
2108
|
? remainingArgs
|
|
2109
2109
|
: remainingArgs.slice(1);
|
|
2110
2110
|
const jsonOutput = sizeFlags.includes("--json");
|
|
2111
|
-
const
|
|
2111
|
+
const npmPack = sizeFlags.includes("--npm");
|
|
2112
|
+
const report = await buildDoctorSize(sizeTarget, { npmPack });
|
|
2112
2113
|
const output = jsonOutput
|
|
2113
2114
|
? renderDoctorSizeJson(report)
|
|
2114
2115
|
: renderDoctorSize(report);
|
|
@@ -2905,6 +2906,13 @@ export async function runCli(args, io = defaultIo, options = {}) {
|
|
|
2905
2906
|
: normalizedFlags[runtimeApprovalDigestIndex + 1];
|
|
2906
2907
|
const changedSinceIndex = normalizedFlags.indexOf("--changed-since");
|
|
2907
2908
|
const changedSinceRef = changedSinceIndex === -1 ? null : normalizedFlags[changedSinceIndex + 1];
|
|
2909
|
+
const failOnRules = [];
|
|
2910
|
+
for (let i = 0; i < normalizedFlags.length; i += 1) {
|
|
2911
|
+
if (normalizedFlags[i] === "--fail-on" && normalizedFlags[i + 1] && !normalizedFlags[i + 1].startsWith("--")) {
|
|
2912
|
+
failOnRules.push(normalizedFlags[i + 1]);
|
|
2913
|
+
i += 1;
|
|
2914
|
+
}
|
|
2915
|
+
}
|
|
2908
2916
|
const baselineIndex = normalizedFlags.indexOf("--baseline");
|
|
2909
2917
|
const baselinePath = baselineIndex === -1 ? null : normalizedFlags[baselineIndex + 1];
|
|
2910
2918
|
if (outputIndex !== -1 && (!outputPath || outputPath.startsWith("--"))) {
|
|
@@ -3150,6 +3158,28 @@ export async function runCli(args, io = defaultIo, options = {}) {
|
|
|
3150
3158
|
failOnWarnings: doctorConfig.failOnWarnings
|
|
3151
3159
|
})
|
|
3152
3160
|
: configuredResult;
|
|
3161
|
+
if (failOnRules.length > 0) {
|
|
3162
|
+
result.findings = result.findings.map((finding) => {
|
|
3163
|
+
if (finding.severity === "warn" && failOnRules.includes(finding.id)) {
|
|
3164
|
+
return { ...finding, severity: "fail" };
|
|
3165
|
+
}
|
|
3166
|
+
return finding;
|
|
3167
|
+
});
|
|
3168
|
+
const hasFail = result.findings.some((f) => f.severity === "fail");
|
|
3169
|
+
const hasWarn = result.findings.some((f) => f.severity === "warn");
|
|
3170
|
+
if (hasFail) {
|
|
3171
|
+
result.status = "fail";
|
|
3172
|
+
result.exitCode = 1;
|
|
3173
|
+
}
|
|
3174
|
+
else if (hasWarn) {
|
|
3175
|
+
result.status = "warn";
|
|
3176
|
+
result.exitCode = 0;
|
|
3177
|
+
}
|
|
3178
|
+
else {
|
|
3179
|
+
result.status = "pass";
|
|
3180
|
+
result.exitCode = 0;
|
|
3181
|
+
}
|
|
3182
|
+
}
|
|
3153
3183
|
if (renderer) {
|
|
3154
3184
|
if (result.status === "fail") {
|
|
3155
3185
|
renderer.stopFailure("Validation failed");
|
package/package.json
CHANGED