@codacy/verity-cli 0.29.4-experimental.c9a3712 → 0.29.4-experimental.f2e812c

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.
Files changed (2) hide show
  1. package/bin/verity.js +130 -15
  2. package/package.json +1 -1
package/bin/verity.js CHANGED
@@ -10390,11 +10390,11 @@ var MAX_DELTA_BYTES = 194560;
10390
10390
  var MAX_FILES = 40;
10391
10391
  var MAX_FILE_BYTES = 51200;
10392
10392
  var DEBOUNCE_SECONDS = 30;
10393
- var MAX_SPEC_FILES = 10;
10394
- var MAX_SPEC_FILE_BYTES = 10240;
10395
- var MAX_TOTAL_SPEC_BYTES = 30720;
10393
+ var MAX_SPEC_FILES = 6;
10394
+ var MAX_SPEC_FILE_BYTES = 512e3;
10395
+ var MAX_TOTAL_SPEC_BYTES = 512e3;
10396
10396
  var MAX_PLAN_FILES = 3;
10397
- var MAX_PLAN_FILE_BYTES = 10240;
10397
+ var MAX_PLAN_FILE_BYTES = 512e3;
10398
10398
  var MAX_INTENT_CHARS = 2e3;
10399
10399
  var SNAPSHOT_DIR = `${VERITY_DIR}/.snapshot`;
10400
10400
  var BASELINE_DIR = `${VERITY_DIR}/.baseline`;
@@ -16765,6 +16765,30 @@ function formatRunEvidence(run, startedAt) {
16765
16765
  out += row("", `${cov.outsideRepo} authored path(s) refused as outside the repo`);
16766
16766
  }
16767
16767
  }
16768
+ if (run.foldResult?.tools?.length) {
16769
+ const shown = run.foldResult.tools.slice(0, 6).map((t) => {
16770
+ const outcome = t.failed > 0 ? `${t.failed} failed` : t.last_status === 0 ? "ok" : "?";
16771
+ const where = t.targets.length > 0 ? ` \u2192 ${t.targets.slice(0, 2).join(", ")}` : "";
16772
+ return `${t.runs}\xD7 ${t.name} (${outcome})${where}`;
16773
+ });
16774
+ const more = run.foldResult.tools.length > 6 ? ` \u2026 +${run.foldResult.tools.length - 6} more` : "";
16775
+ out += row("tools", shown.join(" \xB7 ") + more);
16776
+ if (run.foldResult.coverage.toolNamesDropped > 0) {
16777
+ out += row("", `\u26A0 ${run.foldResult.coverage.toolNamesDropped} tool name(s) refused by the cap`);
16778
+ }
16779
+ }
16780
+ if (run.foldResult?.tasks?.length) {
16781
+ const t = run.foldResult.tasks;
16782
+ const done2 = t.filter((x) => x.status === "completed").length;
16783
+ out += row("tasks", `${t.length} \xB7 ${done2} completed \xB7 ` + list(t.slice(0, 4).map((x) => `#${x.id} ${x.name} [${x.status}]`), 4));
16784
+ }
16785
+ if (run.specs?.length) {
16786
+ const readThisSession = new Set(run.actionSummary?.files_read ?? []);
16787
+ const labelled = run.specs.map(
16788
+ (s) => `${s.path}${readThisSession.has(s.path) ? " (read)" : " (positional)"}`
16789
+ );
16790
+ out += row("specs", `${run.specs.length} \xB7 ${list(labelled, 5)}`);
16791
+ }
16768
16792
  if (run.staticResults.findings.length > 0) {
16769
16793
  out += row("static", `${run.staticResults.findings.length} finding(s) from ${run.staticResults.summary.tools_run.join(", ") || "no tools"}`);
16770
16794
  }
@@ -17216,7 +17240,7 @@ function channelSilence(input) {
17216
17240
  // src/lib/cli-version.ts
17217
17241
  function cliVersion() {
17218
17242
  try {
17219
- return true ? "0.29.4-experimental.c9a3712" : "dev";
17243
+ return true ? "0.29.4-experimental.f2e812c" : "dev";
17220
17244
  } catch {
17221
17245
  return "dev";
17222
17246
  }
@@ -17567,18 +17591,26 @@ var SPEC_CANDIDATES = [
17567
17591
  "docs/API.md",
17568
17592
  "spec/ARCHITECTURE.md"
17569
17593
  ];
17570
- function discoverSpecs() {
17594
+ var DOC_EXT = /\.(md|mdx|ya?ml|txt|rst|adoc)$/i;
17595
+ var UNCONSULTED_FILE_BYTES = 10240;
17596
+ var UNCONSULTED_TOTAL_BYTES = 30720;
17597
+ function discoverSpecs(consulted = []) {
17571
17598
  const result = [];
17572
17599
  const seen = /* @__PURE__ */ new Set();
17573
17600
  let totalBytes = 0;
17574
- const addSpec = (specPath) => {
17601
+ const consultedDocs = new Set(
17602
+ consulted.filter((p) => DOC_EXT.test(p) && !p.startsWith("/") && !p.includes(".."))
17603
+ );
17604
+ const addSpec = (specPath, relevant = false) => {
17575
17605
  if (result.length >= MAX_SPEC_FILES) return false;
17576
- if (totalBytes >= MAX_TOTAL_SPEC_BYTES) return false;
17606
+ const totalCap = relevant ? MAX_TOTAL_SPEC_BYTES : UNCONSULTED_TOTAL_BYTES;
17607
+ if (totalBytes >= totalCap) return false;
17577
17608
  if (seen.has(specPath)) return true;
17578
17609
  if (!(0, import_node_fs21.existsSync)(specPath)) return true;
17579
17610
  seen.add(specPath);
17580
- const remaining = MAX_TOTAL_SPEC_BYTES - totalBytes;
17581
- const readBytes = Math.min(MAX_SPEC_FILE_BYTES, remaining);
17611
+ const remaining = totalCap - totalBytes;
17612
+ const fileCap = relevant ? MAX_SPEC_FILE_BYTES : UNCONSULTED_FILE_BYTES;
17613
+ const readBytes = Math.min(fileCap, remaining);
17582
17614
  try {
17583
17615
  const buf = Buffer.alloc(readBytes);
17584
17616
  const fd = (0, import_node_fs21.openSync)(specPath, "r");
@@ -17592,6 +17624,9 @@ function discoverSpecs() {
17592
17624
  }
17593
17625
  return true;
17594
17626
  };
17627
+ for (const doc of consultedDocs) {
17628
+ if (!addSpec(doc, true)) break;
17629
+ }
17595
17630
  for (const candidate of SPEC_CANDIDATES) {
17596
17631
  if (!addSpec(candidate)) break;
17597
17632
  }
@@ -17662,7 +17697,7 @@ function discoverPlans() {
17662
17697
  async function intentInputs(run) {
17663
17698
  const { actionSummary, allForReview, assistantResponse, baseline, baselineSessionId } = run;
17664
17699
  const conversation = await readAndClearConversationBuffer(baselineSessionId);
17665
- const specs = discoverSpecs();
17700
+ const specs = discoverSpecs(actionSummary?.files_read ?? []);
17666
17701
  const plans = discoverPlans();
17667
17702
  const agentAuthoredCodeThisTurn = !!(actionSummary && (actionSummary.files_edited.length > 0 || actionSummary.files_created.length > 0));
17668
17703
  const turnAuthoredCode = agentAuthoredCodeThisTurn || !!baseline && allForReview.some((f) => changedSinceBaseline(f, baseline));
@@ -18178,6 +18213,18 @@ function commandShape(cmd) {
18178
18213
  return out.join(" ").slice(0, COMMAND_HEAD_CHARS);
18179
18214
  }
18180
18215
  var COMMAND_HEAD_CHARS = 80;
18216
+ var MAX_TOOL_NAMES = 64;
18217
+ var MAX_TOOL_TARGETS = 3;
18218
+ var MAX_TASKS = 64;
18219
+ var TASK_NAME_CHARS = 120;
18220
+ function toolTarget(name, input) {
18221
+ if (name === "Bash") return null;
18222
+ for (const key of ["file_path", "notebook_path", "path", "filePath"]) {
18223
+ const v = input[key];
18224
+ if (typeof v === "string" && v) return v.slice(0, 120);
18225
+ }
18226
+ return null;
18227
+ }
18181
18228
  var rootCandidateCache = /* @__PURE__ */ new Map();
18182
18229
  function candidateRoots(repoRoot2) {
18183
18230
  const cached2 = rootCandidateCache.get(repoRoot2);
@@ -18220,6 +18267,8 @@ function fold(transcriptPath, opts = {}) {
18220
18267
  authored: [],
18221
18268
  unobserved: [],
18222
18269
  commands: [],
18270
+ tools: [],
18271
+ tasks: [],
18223
18272
  unknownTypes: [],
18224
18273
  coverage: {
18225
18274
  recordCounts: {},
@@ -18227,6 +18276,7 @@ function fold(transcriptPath, opts = {}) {
18227
18276
  malformed: 0,
18228
18277
  subagentFiles: 0,
18229
18278
  outsideRepo: 0,
18279
+ toolNamesDropped: 0,
18230
18280
  dispatched: 0,
18231
18281
  userMessages: 0,
18232
18282
  subagentSkipped: 0,
@@ -18237,6 +18287,10 @@ function fold(transcriptPath, opts = {}) {
18237
18287
  const byPath = /* @__PURE__ */ new Map();
18238
18288
  const commandStats = /* @__PURE__ */ new Map();
18239
18289
  const pendingByToolUse = /* @__PURE__ */ new Map();
18290
+ const toolStats = /* @__PURE__ */ new Map();
18291
+ const pendingToolName = /* @__PURE__ */ new Map();
18292
+ const taskById = /* @__PURE__ */ new Map();
18293
+ const pendingTaskName = /* @__PURE__ */ new Map();
18240
18294
  const unknown = /* @__PURE__ */ new Set();
18241
18295
  const ingest = (raw, owner) => {
18242
18296
  for (const line of raw.split("\n")) {
@@ -18256,7 +18310,7 @@ function fold(transcriptPath, opts = {}) {
18256
18310
  result.coverage.compactions++;
18257
18311
  }
18258
18312
  if (type === "user" && hasUserText(record)) result.coverage.userMessages++;
18259
- collectFromRecord(record, owner, byPath, commandStats, pendingByToolUse, opts.repoRoot, result.coverage);
18313
+ collectFromRecord(record, owner, byPath, commandStats, pendingByToolUse, toolStats, pendingToolName, taskById, pendingTaskName, opts.repoRoot, result.coverage);
18260
18314
  }
18261
18315
  };
18262
18316
  try {
@@ -18314,6 +18368,14 @@ function fold(transcriptPath, opts = {}) {
18314
18368
  result.authored = [...byPath.values()].sort((a, b) => a.p.localeCompare(b.p));
18315
18369
  result.unknownTypes = [...unknown].sort();
18316
18370
  result.commands = [...commandStats.entries()].map(([cls, s]) => ({ class: cls, ...s })).sort((a, b) => a.class.localeCompare(b.class));
18371
+ result.tools = [...toolStats.entries()].map(([name, s]) => ({
18372
+ name,
18373
+ runs: s.runs,
18374
+ failed: s.failed,
18375
+ last_status: s.last_status,
18376
+ targets: [...s.targets].map((t) => toRepoRelative(t, opts.repoRoot)).sort()
18377
+ })).sort((a, b) => b.runs - a.runs || a.name.localeCompare(b.name));
18378
+ result.tasks = [...taskById.entries()].map(([id, t]) => ({ id, name: t.name, status: t.status })).sort((a, b) => (Number(a.id) || 0) - (Number(b.id) || 0));
18317
18379
  const authoredPaths = new Set(result.authored.map((a) => a.p));
18318
18380
  for (const raw of opts.changedFiles ?? []) {
18319
18381
  const p = toRepoRelative(raw, opts.repoRoot);
@@ -18332,7 +18394,7 @@ function classifyUnobserved(path) {
18332
18394
  if (/\.(png|jpg|jpeg|gif|pdf|zip|woff2?|ico|mp4)$/i.test(path)) return "binary";
18333
18395
  return "no_edit_record";
18334
18396
  }
18335
- function collectFromRecord(record, owner, byPath, commandStats, pendingByToolUse, repoRoot2, tally) {
18397
+ function collectFromRecord(record, owner, byPath, commandStats, pendingByToolUse, toolStats, pendingToolName, taskById, pendingTaskName, repoRoot2, tally) {
18336
18398
  const message = record.message;
18337
18399
  const content = message?.content ?? record.content;
18338
18400
  const blocks = Array.isArray(content) ? content : content && typeof content === "object" ? [content] : [];
@@ -18341,6 +18403,32 @@ function collectFromRecord(record, owner, byPath, commandStats, pendingByToolUse
18341
18403
  if (blockType === "tool_use") {
18342
18404
  const name = String(block.name ?? "");
18343
18405
  const input = block.input ?? {};
18406
+ if (name && toolStats.size < MAX_TOOL_NAMES) {
18407
+ const prev = toolStats.get(name) ?? { runs: 0, failed: 0, last_status: null, targets: /* @__PURE__ */ new Set() };
18408
+ prev.targets = prev.targets ?? /* @__PURE__ */ new Set();
18409
+ if (prev.targets.size < MAX_TOOL_TARGETS) {
18410
+ const target = toolTarget(name, input);
18411
+ if (target) prev.targets.add(target);
18412
+ }
18413
+ toolStats.set(name, { runs: prev.runs + 1, failed: prev.failed, last_status: null, targets: prev.targets });
18414
+ const toolId = typeof block.id === "string" ? block.id : null;
18415
+ if (toolId) pendingToolName.set(toolId, name);
18416
+ } else if (name && tally) {
18417
+ tally.toolNamesDropped += 1;
18418
+ }
18419
+ if (name === "TaskCreate") {
18420
+ const subject = typeof input.subject === "string" ? input.subject : "";
18421
+ const taskId = typeof block.id === "string" ? block.id : null;
18422
+ if (subject && taskId) pendingTaskName.set(taskId, subject.slice(0, TASK_NAME_CHARS));
18423
+ }
18424
+ if (name === "TaskUpdate") {
18425
+ const id = typeof input.taskId === "string" ? input.taskId : "";
18426
+ const status = typeof input.status === "string" ? input.status : "";
18427
+ if (id && status) {
18428
+ const entry = taskById.get(id);
18429
+ taskById.set(id, { name: entry?.name ?? `#${id}`, status });
18430
+ }
18431
+ }
18344
18432
  if (EDIT_TOOLS.has(name)) {
18345
18433
  const rawPath = typeof input.notebook_path === "string" ? input.notebook_path : typeof input.file_path === "string" ? input.file_path : null;
18346
18434
  if (rawPath && !isInsideRepo(rawPath, repoRoot2)) {
@@ -18380,6 +18468,31 @@ function collectFromRecord(record, owner, byPath, commandStats, pendingByToolUse
18380
18468
  }
18381
18469
  if (blockType === "tool_result") {
18382
18470
  const id = typeof block.tool_use_id === "string" ? block.tool_use_id : null;
18471
+ const taskName = id ? pendingTaskName.get(id) : void 0;
18472
+ if (taskName) {
18473
+ pendingTaskName.delete(id);
18474
+ const body = typeof block.content === "string" ? block.content : "";
18475
+ const created = /Task #(\d+)/.exec(body);
18476
+ if (created && taskById.size < MAX_TASKS) {
18477
+ taskById.set(created[1], { name: taskName, status: taskById.get(created[1])?.status ?? "created" });
18478
+ }
18479
+ }
18480
+ const toolName = id ? pendingToolName.get(id) : void 0;
18481
+ if (toolName) {
18482
+ pendingToolName.delete(id);
18483
+ const prevTool = toolStats.get(toolName);
18484
+ if (prevTool) {
18485
+ const failed = block.is_error === true;
18486
+ toolStats.set(toolName, {
18487
+ runs: prevTool.runs,
18488
+ failed: prevTool.failed + (failed ? 1 : 0),
18489
+ last_status: block.is_error === true ? 1 : block.is_error === false ? 0 : null,
18490
+ // Carried, not rebuilt: the targets were collected on the `tool_use`
18491
+ // side and dropping them here would empty the ledger on every result.
18492
+ targets: prevTool.targets
18493
+ });
18494
+ }
18495
+ }
18383
18496
  const cls = id ? pendingByToolUse.get(id) : void 0;
18384
18497
  if (!cls) continue;
18385
18498
  pendingByToolUse.delete(id);
@@ -19373,6 +19486,8 @@ async function buildRequest(run) {
19373
19486
  authored_since_verdict: memorySession ? foldDossier(memorySession.d).authored_all.filter((a) => a.hash_now !== a.hash_at_last_verdict).map((a) => a.path) : [],
19374
19487
  unobserved: foldResult?.unobserved ?? [],
19375
19488
  commands: foldResult?.commands ?? [],
19489
+ tools: foldResult?.tools ?? [],
19490
+ tasks: foldResult?.tasks ?? [],
19376
19491
  unknown_types: foldResult?.unknownTypes ?? [],
19377
19492
  coverage: foldResult?.coverage ?? { recordCounts: {}, totalRecords: 0, malformed: 0, subagentFiles: 0, subagentSkipped: 0, complete: false },
19378
19493
  // INV-19, computed client-side and sent so a conservation failure is
@@ -21999,8 +22114,8 @@ function registerTelemetryCommands(program2) {
21999
22114
  }
22000
22115
 
22001
22116
  // src/cli.ts
22002
- program.name("verity").description("CLI for Verity quality gate service").version("0.29.4-experimental.c9a3712").option("--token <token>", "Override authentication token").option("--service-url <url>", "Override service URL").option("--verbose", "Log HTTP requests/responses to stderr").hook("preAction", async (_thisCommand, actionCommand) => {
22003
- installStderrLog(actionCommand.name(), process.argv.slice(2), "0.29.4-experimental.c9a3712");
22117
+ program.name("verity").description("CLI for Verity quality gate service").version("0.29.4-experimental.f2e812c").option("--token <token>", "Override authentication token").option("--service-url <url>", "Override service URL").option("--verbose", "Log HTTP requests/responses to stderr").hook("preAction", async (_thisCommand, actionCommand) => {
22118
+ installStderrLog(actionCommand.name(), process.argv.slice(2), "0.29.4-experimental.f2e812c");
22004
22119
  setUserNamedServiceUrl(program.opts().serviceUrl);
22005
22120
  try {
22006
22121
  await foldLegacyLocalCredential();
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@codacy/verity-cli",
3
- "version": "0.29.4-experimental.c9a3712",
3
+ "version": "0.29.4-experimental.f2e812c",
4
4
  "description": "CLI for Verity quality gate service",
5
5
  "license": "SEE LICENSE IN LICENSE",
6
6
  "homepage": "https://verity.md",