From b534d0234f701c1db4618af01d471ae88d3e2a00 Mon Sep 17 00:00:00 2001 From: Sarthak Agrawal Date: Tue, 22 Sep 2026 10:08:25 +0530 Subject: [PATCH] Register xray corpus and ai-code-validation in the /api/ai catalog The deploy gate requires every public sitemap route in api-ai.json; sync-xray-examples.mjs now keeps the catalog in step with the corpus. Generated with [Devin](https://devin.ai) Co-Authored-By: Devin <158243242+devin-ai-integration[bot]@users.noreply.github.com> --- apps/landing-page-astro/public/api-ai.json | 175 +++++++++++++++++++++ scripts/sync-xray-examples.mjs | 18 +++ 2 files changed, 193 insertions(+) diff --git a/apps/landing-page-astro/public/api-ai.json b/apps/landing-page-astro/public/api-ai.json index c3ec2f2a..2efe65ea 100644 --- a/apps/landing-page-astro/public/api-ai.json +++ b/apps/landing-page-astro/public/api-ai.json @@ -134,6 +134,13 @@ "kind": "static", "description": "Comparison of static code review and executable verification" }, + { + "id": "ai-code-validation", + "url": "https://codevetter.com/ai-code-validation", + "md": "https://codevetter.com/ai-code-validation.md", + "kind": "static", + "description": "Validation vs verification vs review for agent-generated code, with a practical validation pass" + }, { "id": "compare", "url": "https://codevetter.com/compare", @@ -238,6 +245,174 @@ "md": "https://codevetter.com/xray/py-path-traversal.md", "kind": "static", "description": "Adjudicated Python path-traversal example" + }, + { + "id": "xray-go-errcheck", + "url": "https://codevetter.com/xray/go-errcheck", + "md": "https://codevetter.com/xray/go-errcheck.md", + "kind": "static", + "description": "Adjudicated go unchecked error example" + }, + { + "id": "xray-go-hardcoded-credentials", + "url": "https://codevetter.com/xray/go-hardcoded-credentials", + "md": "https://codevetter.com/xray/go-hardcoded-credentials.md", + "kind": "static", + "description": "Adjudicated go hardcoded secret example" + }, + { + "id": "xray-go-nil-pointer", + "url": "https://codevetter.com/xray/go-nil-pointer", + "md": "https://codevetter.com/xray/go-nil-pointer.md", + "kind": "static", + "description": "Adjudicated go nil dereference example" + }, + { + "id": "xray-go-sql-injection", + "url": "https://codevetter.com/xray/go-sql-injection", + "md": "https://codevetter.com/xray/go-sql-injection.md", + "kind": "static", + "description": "Adjudicated go sql injection example" + }, + { + "id": "xray-java-insecure-random", + "url": "https://codevetter.com/xray/java-insecure-random", + "md": "https://codevetter.com/xray/java-insecure-random.md", + "kind": "static", + "description": "Adjudicated java insecure random example" + }, + { + "id": "xray-js-eval-injection", + "url": "https://codevetter.com/xray/js-eval-injection", + "md": "https://codevetter.com/xray/js-eval-injection.md", + "kind": "static", + "description": "Adjudicated javascript code injection example" + }, + { + "id": "xray-js-open-redirect", + "url": "https://codevetter.com/xray/js-open-redirect", + "md": "https://codevetter.com/xray/js-open-redirect.md", + "kind": "static", + "description": "Adjudicated javascript open redirect example" + }, + { + "id": "xray-py-bare-except", + "url": "https://codevetter.com/xray/py-bare-except", + "md": "https://codevetter.com/xray/py-bare-except.md", + "kind": "static", + "description": "Adjudicated python swallowed error example" + }, + { + "id": "xray-py-command-injection", + "url": "https://codevetter.com/xray/py-command-injection", + "md": "https://codevetter.com/xray/py-command-injection.md", + "kind": "static", + "description": "Adjudicated python command injection example" + }, + { + "id": "xray-py-hardcoded-secret", + "url": "https://codevetter.com/xray/py-hardcoded-secret", + "md": "https://codevetter.com/xray/py-hardcoded-secret.md", + "kind": "static", + "description": "Adjudicated python hardcoded secret example" + }, + { + "id": "xray-py-insecure-deserialization", + "url": "https://codevetter.com/xray/py-insecure-deserialization", + "md": "https://codevetter.com/xray/py-insecure-deserialization.md", + "kind": "static", + "description": "Adjudicated python insecure deserialization example" + }, + { + "id": "xray-py-sql-injection", + "url": "https://codevetter.com/xray/py-sql-injection", + "md": "https://codevetter.com/xray/py-sql-injection.md", + "kind": "static", + "description": "Adjudicated python sql injection example" + }, + { + "id": "xray-py-ssrf", + "url": "https://codevetter.com/xray/py-ssrf", + "md": "https://codevetter.com/xray/py-ssrf.md", + "kind": "static", + "description": "Adjudicated python ssrf example" + }, + { + "id": "xray-py-weak-hash", + "url": "https://codevetter.com/xray/py-weak-hash", + "md": "https://codevetter.com/xray/py-weak-hash.md", + "kind": "static", + "description": "Adjudicated python weak crypto example" + }, + { + "id": "xray-py-zip-bomb", + "url": "https://codevetter.com/xray/py-zip-bomb", + "md": "https://codevetter.com/xray/py-zip-bomb.md", + "kind": "static", + "description": "Adjudicated python resource exhaustion example" + }, + { + "id": "xray-rust-integer-overflow", + "url": "https://codevetter.com/xray/rust-integer-overflow", + "md": "https://codevetter.com/xray/rust-integer-overflow.md", + "kind": "static", + "description": "Adjudicated rust integer overflow example" + }, + { + "id": "xray-ts-dead-code", + "url": "https://codevetter.com/xray/ts-dead-code", + "md": "https://codevetter.com/xray/ts-dead-code.md", + "kind": "static", + "description": "Adjudicated typescript dead code example" + }, + { + "id": "xray-ts-hardcoded-credentials", + "url": "https://codevetter.com/xray/ts-hardcoded-credentials", + "md": "https://codevetter.com/xray/ts-hardcoded-credentials.md", + "kind": "static", + "description": "Adjudicated typescript hardcoded secret example" + }, + { + "id": "xray-ts-insecure-cookie", + "url": "https://codevetter.com/xray/ts-insecure-cookie", + "md": "https://codevetter.com/xray/ts-insecure-cookie.md", + "kind": "static", + "description": "Adjudicated typescript insecure cookie example" + }, + { + "id": "xray-ts-missing-await", + "url": "https://codevetter.com/xray/ts-missing-await", + "md": "https://codevetter.com/xray/ts-missing-await.md", + "kind": "static", + "description": "Adjudicated typescript missing await example" + }, + { + "id": "xray-ts-prototype-pollution", + "url": "https://codevetter.com/xray/ts-prototype-pollution", + "md": "https://codevetter.com/xray/ts-prototype-pollution.md", + "kind": "static", + "description": "Adjudicated typescript prototype pollution example" + }, + { + "id": "xray-ts-regex-dos", + "url": "https://codevetter.com/xray/ts-regex-dos", + "md": "https://codevetter.com/xray/ts-regex-dos.md", + "kind": "static", + "description": "Adjudicated typescript regex dos example" + }, + { + "id": "xray-ts-type-confusion", + "url": "https://codevetter.com/xray/ts-type-confusion", + "md": "https://codevetter.com/xray/ts-type-confusion.md", + "kind": "static", + "description": "Adjudicated typescript type confusion example" + }, + { + "id": "xray-ts-xss", + "url": "https://codevetter.com/xray/ts-xss", + "md": "https://codevetter.com/xray/ts-xss.md", + "kind": "static", + "description": "Adjudicated typescript xss example" } ], "auth": { diff --git a/scripts/sync-xray-examples.mjs b/scripts/sync-xray-examples.mjs index 2be4f858..83c64aec 100644 --- a/scripts/sync-xray-examples.mjs +++ b/scripts/sync-xray-examples.mjs @@ -12,6 +12,7 @@ const ROOT = new URL('..', import.meta.url).pathname; const CASES_DIR = join(ROOT, 'benchmarks/public-catch-rate/cases'); const RESULTS = join(ROOT, 'apps/landing-page-astro/src/data/benchmark-results.json'); const OUT = join(ROOT, 'apps/landing-page-astro/src/data/xray-examples.json'); +const API_AI = join(ROOT, 'apps/landing-page-astro/public/api-ai.json'); const results = JSON.parse(readFileSync(RESULTS, 'utf8')); const byId = new Map(results.codevetter.cases.map((c) => [c.id, c])); @@ -51,6 +52,23 @@ for (const dir of readdirSync(CASES_DIR).sort()) { } writeFileSync(OUT, `${JSON.stringify(entries, null, 2)}\n`, 'utf8'); + +// Every public route must appear in /api/ai's surface catalog (enforced by +// scripts/verify-agent-surfaces.mjs in the deploy workflow). +const catalog = JSON.parse(readFileSync(API_AI, 'utf8')); +const known = new Set(catalog.surfaces.map((s) => s.id)); +for (const entry of entries) { + const id = `xray-${entry.id}`; + if (known.has(id)) continue; + catalog.surfaces.push({ + id, + url: `https://codevetter.com/xray/${entry.id}`, + md: `https://codevetter.com/xray/${entry.id}.md`, + kind: 'static', + description: `Adjudicated ${entry.language} ${String(entry.finding.title).toLowerCase()} example`, + }); +} +writeFileSync(API_AI, `${JSON.stringify(catalog, null, 2)}\n`, 'utf8'); console.log( `xray-examples.json: ${entries.length} cases (${existing.size} preserved, ${entries.length - existing.size} generated)` );