agentaudit 3.9.32 → 3.9.34
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/cli.mjs +63 -2
- package/index.mjs +36 -2
- package/package.json +1 -1
package/cli.mjs
CHANGED
|
@@ -1704,6 +1704,17 @@ async function auditRepo(url) {
|
|
|
1704
1704
|
|
|
1705
1705
|
// Upload to registry
|
|
1706
1706
|
const creds = loadCredentials();
|
|
1707
|
+
const finalModel = providerMeta.reported_model || actualModel;
|
|
1708
|
+
const finalProvider = resolvedProvider.id;
|
|
1709
|
+
if (!finalModel || finalModel === 'unknown') {
|
|
1710
|
+
console.log(` ${c.yellow}⚠ Model not detected — report will not include model attestation.${c.reset}`);
|
|
1711
|
+
console.log(` ${c.dim} This usually means the LLM API did not return model info.${c.reset}`);
|
|
1712
|
+
console.log(` ${c.dim} Try: agentaudit config set model <model-name>${c.reset}`);
|
|
1713
|
+
if (process.argv.includes('--debug')) {
|
|
1714
|
+
console.log(` ${c.dim} providerMeta: ${JSON.stringify(providerMeta)}${c.reset}`);
|
|
1715
|
+
console.log(` ${c.dim} actualModel: ${actualModel}, resolvedProvider: ${resolvedProvider.id}${c.reset}`);
|
|
1716
|
+
}
|
|
1717
|
+
}
|
|
1707
1718
|
if (creds) {
|
|
1708
1719
|
process.stdout.write(` Uploading report to registry...`);
|
|
1709
1720
|
try {
|
|
@@ -1717,8 +1728,8 @@ async function auditRepo(url) {
|
|
|
1717
1728
|
...report,
|
|
1718
1729
|
commit_sha: report.commit_sha || repoCommitSha || undefined,
|
|
1719
1730
|
package_version: report.package_version || repoPackageVersion || undefined,
|
|
1720
|
-
audit_model:
|
|
1721
|
-
audit_provider:
|
|
1731
|
+
audit_model: finalModel !== 'unknown' ? finalModel : undefined,
|
|
1732
|
+
audit_provider: finalProvider,
|
|
1722
1733
|
provider_msg_id: providerMeta.provider_msg_id || undefined,
|
|
1723
1734
|
provider_fingerprint: providerMeta.provider_fingerprint || undefined,
|
|
1724
1735
|
input_tokens: providerMeta.input_tokens || undefined,
|
|
@@ -1732,13 +1743,63 @@ async function auditRepo(url) {
|
|
|
1732
1743
|
const reportSlug = data?.skill_slug || data?.slug || slug;
|
|
1733
1744
|
console.log(` ${c.green}done${c.reset}`);
|
|
1734
1745
|
console.log(` ${c.dim}Report: ${REGISTRY_URL}/skills/${reportSlug}${c.reset}`);
|
|
1746
|
+
// Show API warnings
|
|
1747
|
+
if (data?.warnings?.length) {
|
|
1748
|
+
for (const w of data.warnings) {
|
|
1749
|
+
console.log(` ${c.yellow}⚠ ${w}${c.reset}`);
|
|
1750
|
+
}
|
|
1751
|
+
}
|
|
1735
1752
|
// Refresh stats cache in background
|
|
1736
1753
|
if (creds.agent_name) refreshStatsCache(creds.agent_name).catch(() => {});
|
|
1754
|
+
// Fetch registry consensus after upload
|
|
1755
|
+
try {
|
|
1756
|
+
const regData = await checkRegistry(reportSlug);
|
|
1757
|
+
if (regData) {
|
|
1758
|
+
const regRisk = regData.latest_risk_score ?? regData.risk_score ?? 0;
|
|
1759
|
+
const regTrust = regData.trust_score ?? (100 - regRisk);
|
|
1760
|
+
const totalReports = regData.total_reports ?? 1;
|
|
1761
|
+
const uniqueAgents = regData.unique_agents ?? 1;
|
|
1762
|
+
const confidence = regData.confidence ?? 'unverified';
|
|
1763
|
+
const totalFindings = regData.total_findings ?? 0;
|
|
1764
|
+
const hasOfficial = regData.has_official_audit;
|
|
1765
|
+
|
|
1766
|
+
// Show registry consensus if different from own report or multiple reports exist
|
|
1767
|
+
if (totalReports > 1 || regRisk !== report.risk_score) {
|
|
1768
|
+
console.log();
|
|
1769
|
+
console.log(` ${c.bold}Registry Consensus${c.reset}`);
|
|
1770
|
+
const trustColor = regTrust >= 70 ? c.green : regTrust >= 40 ? c.yellow : c.red;
|
|
1771
|
+
const trustLabel = regTrust >= 70 ? 'SAFE' : regTrust >= 40 ? 'CAUTION' : 'UNSAFE';
|
|
1772
|
+
console.log(` ${trustColor}${c.bold}${trustLabel}${c.reset} Trust Score: ${trustColor}${regTrust}/100${c.reset} ${c.dim}(across ${totalReports} reports from ${uniqueAgents} auditor${uniqueAgents !== 1 ? 's' : ''})${c.reset}`);
|
|
1773
|
+
if (totalFindings > 0) {
|
|
1774
|
+
console.log(` ${c.dim}Total findings across all reports: ${totalFindings}${c.reset}`);
|
|
1775
|
+
}
|
|
1776
|
+
const confDisplay = {
|
|
1777
|
+
consensus: { icon: '🟢', label: 'Consensus Certified', color: c.green },
|
|
1778
|
+
verified: { icon: '🟢', label: 'Verified', color: c.green },
|
|
1779
|
+
low: { icon: '🟡', label: 'Low Confidence', color: c.yellow },
|
|
1780
|
+
unverified: { icon: '🔴', label: 'Unverified', color: c.yellow },
|
|
1781
|
+
}[confidence] || { icon: '⚪', label: confidence, color: c.dim };
|
|
1782
|
+
console.log(` ${confDisplay.icon} ${confDisplay.color}${confDisplay.label}${c.reset}`);
|
|
1783
|
+
if (hasOfficial) console.log(` ${c.green}✔ Officially audited${c.reset}`);
|
|
1784
|
+
|
|
1785
|
+
// Warn if own report disagrees with consensus
|
|
1786
|
+
const ownRisk = report.risk_score || 0;
|
|
1787
|
+
if (Math.abs(ownRisk - regRisk) > 10) {
|
|
1788
|
+
console.log();
|
|
1789
|
+
console.log(` ${c.yellow}⚠ Your audit (risk ${ownRisk}) differs from registry consensus (risk ${regRisk}).${c.reset}`);
|
|
1790
|
+
console.log(` ${c.dim} This may indicate model-specific blind spots or a changing codebase.${c.reset}`);
|
|
1791
|
+
}
|
|
1792
|
+
}
|
|
1793
|
+
}
|
|
1794
|
+
} catch {}
|
|
1737
1795
|
} else {
|
|
1796
|
+
const errBody = await res.text().catch(() => '');
|
|
1738
1797
|
console.log(` ${c.yellow}failed (HTTP ${res.status})${c.reset}`);
|
|
1798
|
+
if (process.argv.includes('--debug')) console.log(` ${c.dim}Response: ${errBody.slice(0, 500)}${c.reset}`);
|
|
1739
1799
|
}
|
|
1740
1800
|
} catch (err) {
|
|
1741
1801
|
console.log(` ${c.yellow}failed${c.reset}`);
|
|
1802
|
+
if (process.argv.includes('--debug')) console.log(` ${c.dim}Error: ${err.message}${c.reset}`);
|
|
1742
1803
|
}
|
|
1743
1804
|
} else {
|
|
1744
1805
|
console.log(` ${c.dim}Run ${c.cyan}agentaudit setup${c.dim} to upload reports to the registry${c.reset}`);
|
package/index.mjs
CHANGED
|
@@ -534,7 +534,27 @@ server.setRequestHandler(CallToolRequestSchema, async (request) => {
|
|
|
534
534
|
try { data = JSON.parse(body); } catch { data = { raw: body }; }
|
|
535
535
|
|
|
536
536
|
if (res.ok) {
|
|
537
|
-
|
|
537
|
+
const reportSlug = data?.skill_slug || report.skill_slug;
|
|
538
|
+
// Fetch registry consensus to give the agent full decision context
|
|
539
|
+
let consensusInfo = '';
|
|
540
|
+
try {
|
|
541
|
+
const regRes = await fetch(`${REGISTRY_URL}/api/skills/${encodeURIComponent(reportSlug)}`, { signal: AbortSignal.timeout(5000) });
|
|
542
|
+
if (regRes.ok) {
|
|
543
|
+
const reg = await regRes.json();
|
|
544
|
+
const regRisk = reg.latest_risk_score ?? 0;
|
|
545
|
+
const regTrust = reg.trust_score ?? (100 - regRisk);
|
|
546
|
+
const totalReports = reg.total_reports ?? 1;
|
|
547
|
+
const uniqueAgents = reg.unique_agents ?? 1;
|
|
548
|
+
const confidence = reg.confidence ?? 'unverified';
|
|
549
|
+
const totalFindings = reg.total_findings ?? 0;
|
|
550
|
+
const trustLabel = regTrust >= 70 ? 'SAFE' : regTrust >= 40 ? 'CAUTION' : 'UNSAFE';
|
|
551
|
+
consensusInfo = `\n\n📊 **Registry Consensus** (across ${totalReports} reports from ${uniqueAgents} auditor${uniqueAgents !== 1 ? 's' : ''}):\n- Trust Score: ${regTrust}/100 (${trustLabel})\n- Total Findings: ${totalFindings}\n- Confidence: ${confidence}${reg.has_official_audit ? '\n- ✔ Officially audited' : ''}`;
|
|
552
|
+
if (totalReports > 1) {
|
|
553
|
+
consensusInfo += `\n\n⚠️ IMPORTANT: Your audit is ONE data point. The registry consensus reflects ALL audits. If your result differs significantly, this may indicate model-specific blind spots. Agents should use the REGISTRY CONSENSUS (not just this single audit) when making install/trust decisions.`;
|
|
554
|
+
}
|
|
555
|
+
}
|
|
556
|
+
} catch {}
|
|
557
|
+
return { content: [{ type: 'text', text: `✅ Report submitted!\n\nReport ID: ${data.report_id || 'unknown'}\nURL: ${REGISTRY_URL}/skills/${reportSlug}\nYour Audit: Risk ${report.risk_score}/100 (${report.result}), ${report.findings_count} findings${consensusInfo}` }] };
|
|
538
558
|
} else {
|
|
539
559
|
return { content: [{ type: 'text', text: `Upload failed (HTTP ${res.status}): ${JSON.stringify(data, null, 2)}` }] };
|
|
540
560
|
}
|
|
@@ -584,8 +604,22 @@ server.setRequestHandler(CallToolRequestSchema, async (request) => {
|
|
|
584
604
|
summary += `⚠️ OUTDATED: The package has changed since the last audit. Consider running a fresh audit first.\n\n`;
|
|
585
605
|
}
|
|
586
606
|
|
|
607
|
+
// Consensus section — critical for agent decision-making
|
|
608
|
+
const totalReports = data.total_reports ?? 1;
|
|
609
|
+
const uniqueAgents = data.unique_agents ?? 1;
|
|
610
|
+
const confidence = data.confidence ?? 'unverified';
|
|
611
|
+
const trustScore = data.trust_score ?? (100 - (risk || 0));
|
|
612
|
+
const trustLabel = trustScore >= 70 ? 'SAFE' : trustScore >= 40 ? 'CAUTION' : 'UNSAFE';
|
|
613
|
+
|
|
614
|
+
summary += `--- Registry Consensus ---\n`;
|
|
615
|
+
summary += `Trust Score: ${trustScore}/100 (${trustLabel})\n`;
|
|
616
|
+
summary += `Reports: ${totalReports} from ${uniqueAgents} independent auditor${uniqueAgents !== 1 ? 's' : ''}\n`;
|
|
617
|
+
summary += `Confidence: ${confidence}\n`;
|
|
618
|
+
if (confidence === 'unverified') summary += `⚠️ Only 1 audit exists — consider running your own for independent verification.\n`;
|
|
619
|
+
if (confidence === 'low') summary += `⚠️ Limited independent verification — more auditors needed for consensus.\n`;
|
|
620
|
+
|
|
587
621
|
// Details section
|
|
588
|
-
summary +=
|
|
622
|
+
summary += `\n--- Details ---\n`;
|
|
589
623
|
summary += `Package: ${package_name}\n`;
|
|
590
624
|
summary += `Status: ${official}\n`;
|
|
591
625
|
summary += `Last Audited: ${auditedAt}\n`;
|