@cejel/cejel 0.1.2 → 0.1.4

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.
@@ -29,7 +29,7 @@ var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__ge
29
29
  mod
30
30
  ));
31
31
 
32
- // ../witan/src/external-findings.ts
32
+ // src/witan/external-findings.ts
33
33
  var EXTERNAL_FINDINGS_DISPLAY_LIMIT = 10;
34
34
  var SEVERITY_RANK = {
35
35
  critical: 0,
@@ -82,7 +82,7 @@ function collectExternalFindings(consumedSignals) {
82
82
  });
83
83
  }
84
84
 
85
- // ../witan/src/html.ts
85
+ // src/witan/html.ts
86
86
  function renderWitanHtmlReport(report) {
87
87
  const codeCriteria = criteriaByCategory(report, "code_trust");
88
88
  const processCriteria = criteriaByCategory(report, "process_trust");
@@ -106,7 +106,7 @@ function renderWitanHtmlReport(report) {
106
106
  <header class="hero">
107
107
  <div class="brand">
108
108
  <span class="brand-mark" aria-hidden="true">C</span>
109
- <span class="brand-name">Cejel / Alfred</span>
109
+ <span class="brand-name">Cejel</span>
110
110
  </div>
111
111
  <div class="hero-grid">
112
112
  <section>
@@ -403,7 +403,7 @@ a:hover { text-decoration: underline; text-underline-offset: 2px; }
403
403
  }
404
404
  `;
405
405
 
406
- // ../witan/src/badge.ts
406
+ // src/witan/badge.ts
407
407
  var VERDICT_COLOR = {
408
408
  Verified: "brightgreen",
409
409
  Conditional: "yellow",
@@ -470,15 +470,10 @@ function escapeXml(value) {
470
470
  return value.replace(/&/g, "&amp;").replace(/</g, "&lt;").replace(/>/g, "&gt;").replace(/"/g, "&quot;");
471
471
  }
472
472
 
473
- // ../witan/src/claim-reality.ts
474
- import { existsSync, readFileSync, readdirSync, statSync } from "fs";
475
- import { join } from "path";
476
-
477
- // ../witan/src/leaderboard.ts
478
- import { existsSync as existsSync2, mkdirSync as mkdirSync3, readFileSync as readFileSync8, writeFileSync as writeFileSync2 } from "fs";
479
- import { join as join6 } from "path";
473
+ // src/witan/attestation.ts
474
+ import { createHash } from "crypto";
480
475
 
481
- // ../../node_modules/.pnpm/zod@3.25.76/node_modules/zod/v3/external.js
476
+ // node_modules/.pnpm/zod@3.25.76/node_modules/zod/v3/external.js
482
477
  var external_exports = {};
483
478
  __export(external_exports, {
484
479
  BRAND: () => BRAND,
@@ -590,7 +585,7 @@ __export(external_exports, {
590
585
  void: () => voidType
591
586
  });
592
587
 
593
- // ../../node_modules/.pnpm/zod@3.25.76/node_modules/zod/v3/helpers/util.js
588
+ // node_modules/.pnpm/zod@3.25.76/node_modules/zod/v3/helpers/util.js
594
589
  var util;
595
590
  (function(util2) {
596
591
  util2.assertEqual = (_) => {
@@ -724,7 +719,7 @@ var getParsedType = (data) => {
724
719
  }
725
720
  };
726
721
 
727
- // ../../node_modules/.pnpm/zod@3.25.76/node_modules/zod/v3/ZodError.js
722
+ // node_modules/.pnpm/zod@3.25.76/node_modules/zod/v3/ZodError.js
728
723
  var ZodIssueCode = util.arrayToEnum([
729
724
  "invalid_type",
730
725
  "invalid_literal",
@@ -842,7 +837,7 @@ ZodError.create = (issues) => {
842
837
  return error;
843
838
  };
844
839
 
845
- // ../../node_modules/.pnpm/zod@3.25.76/node_modules/zod/v3/locales/en.js
840
+ // node_modules/.pnpm/zod@3.25.76/node_modules/zod/v3/locales/en.js
846
841
  var errorMap = (issue, _ctx) => {
847
842
  let message;
848
843
  switch (issue.code) {
@@ -945,7 +940,7 @@ var errorMap = (issue, _ctx) => {
945
940
  };
946
941
  var en_default = errorMap;
947
942
 
948
- // ../../node_modules/.pnpm/zod@3.25.76/node_modules/zod/v3/errors.js
943
+ // node_modules/.pnpm/zod@3.25.76/node_modules/zod/v3/errors.js
949
944
  var overrideErrorMap = en_default;
950
945
  function setErrorMap(map) {
951
946
  overrideErrorMap = map;
@@ -954,7 +949,7 @@ function getErrorMap() {
954
949
  return overrideErrorMap;
955
950
  }
956
951
 
957
- // ../../node_modules/.pnpm/zod@3.25.76/node_modules/zod/v3/helpers/parseUtil.js
952
+ // node_modules/.pnpm/zod@3.25.76/node_modules/zod/v3/helpers/parseUtil.js
958
953
  var makeIssue = (params) => {
959
954
  const { data, path, errorMaps, issueData } = params;
960
955
  const fullPath = [...path, ...issueData.path || []];
@@ -1064,14 +1059,14 @@ var isDirty = (x) => x.status === "dirty";
1064
1059
  var isValid = (x) => x.status === "valid";
1065
1060
  var isAsync = (x) => typeof Promise !== "undefined" && x instanceof Promise;
1066
1061
 
1067
- // ../../node_modules/.pnpm/zod@3.25.76/node_modules/zod/v3/helpers/errorUtil.js
1062
+ // node_modules/.pnpm/zod@3.25.76/node_modules/zod/v3/helpers/errorUtil.js
1068
1063
  var errorUtil;
1069
1064
  (function(errorUtil2) {
1070
1065
  errorUtil2.errToObj = (message) => typeof message === "string" ? { message } : message || {};
1071
1066
  errorUtil2.toString = (message) => typeof message === "string" ? message : message?.message;
1072
1067
  })(errorUtil || (errorUtil = {}));
1073
1068
 
1074
- // ../../node_modules/.pnpm/zod@3.25.76/node_modules/zod/v3/types.js
1069
+ // node_modules/.pnpm/zod@3.25.76/node_modules/zod/v3/types.js
1075
1070
  var ParseInputLazyPath = class {
1076
1071
  constructor(parent, value, path, key) {
1077
1072
  this._cachedPath = [];
@@ -4519,849 +4514,7 @@ var coerce = {
4519
4514
  };
4520
4515
  var NEVER = INVALID;
4521
4516
 
4522
- // ../shared/src/types/attestation.ts
4523
- var attestationOutcomeSchema = external_exports.enum([
4524
- "ATTESTED_READY",
4525
- "ATTESTED_WITH_GAPS",
4526
- "NOT_READY",
4527
- "REVOKED"
4528
- ]);
4529
- var attestationKindSchema = external_exports.enum(["OPERATOR_READINESS", "EXTERNAL_ASSESSOR_REFERENCE"]);
4530
- var attestationEvidenceRefKindSchema = external_exports.enum([
4531
- "runbook_path",
4532
- "github_run_url",
4533
- "vercel_deployment_id",
4534
- "neon_query_evidence",
4535
- "report_hash",
4536
- "external_assessor_ref"
4537
- ]);
4538
- var attestationEvidenceRefSchema = external_exports.object({
4539
- kind: attestationEvidenceRefKindSchema,
4540
- /** Redacted reference string (path, URL, ID, or hash). Max 512 chars. */
4541
- ref: external_exports.string().min(1).max(512),
4542
- /** Optional one-line redacted description. */
4543
- note: external_exports.string().max(280).optional()
4544
- });
4545
- var createAttestationInputSchema = external_exports.object({
4546
- studioId: external_exports.string().uuid(),
4547
- complianceProfileId: external_exports.string().uuid(),
4548
- productId: external_exports.string().uuid().nullable().optional(),
4549
- framework: external_exports.string().min(1).max(120),
4550
- kind: attestationKindSchema,
4551
- outcome: attestationOutcomeSchema,
4552
- /** Redacted operator statement; no payloads. */
4553
- statement: external_exports.string().min(1).max(4e3),
4554
- evidenceRefs: external_exports.array(attestationEvidenceRefSchema).min(1),
4555
- supersedesAttestationId: external_exports.string().uuid().nullable().optional(),
4556
- metadata: external_exports.record(external_exports.unknown()).default({})
4557
- });
4558
-
4559
- // ../shared/src/types/standup-provisioning.ts
4560
- var ScaffoldFileSchema = external_exports.object({
4561
- path: external_exports.string().min(1),
4562
- contents: external_exports.string()
4563
- }).strict();
4564
- var ScaffoldManifestSchema = external_exports.array(ScaffoldFileSchema).min(1);
4565
- var RepoRefSchema = external_exports.object({
4566
- studioId: external_exports.string().uuid(),
4567
- owner: external_exports.string().min(1),
4568
- // GitHub org/account that owns the repo
4569
- name: external_exports.string().min(1),
4570
- fullName: external_exports.string().min(1),
4571
- // owner/name
4572
- htmlUrl: external_exports.string().url(),
4573
- defaultBranch: external_exports.string().min(1).default("main")
4574
- }).strict();
4575
- var ScopedTokenSchema = external_exports.object({
4576
- token: external_exports.string().min(1),
4577
- expiresAt: external_exports.string(),
4578
- // ISO-8601
4579
- scope: external_exports.string().min(1)
4580
- // human-readable, e.g. "contents:write on owner/name"
4581
- }).strict();
4582
- var BranchProtectionStatusSchema = external_exports.object({
4583
- protected: external_exports.boolean(),
4584
- requiresPullRequestReview: external_exports.boolean(),
4585
- requiredApprovingReviewCount: external_exports.number().int().nonnegative(),
4586
- allowsForcePushes: external_exports.boolean(),
4587
- allowsDeletions: external_exports.boolean()
4588
- }).strict();
4589
- var RenderParamsSchema = external_exports.object({
4590
- productName: external_exports.string().min(1),
4591
- slug: external_exports.string().min(1),
4592
- vertical: external_exports.string().min(1)
4593
- }).strict();
4594
- var TemplateInputFieldSchema = external_exports.object({
4595
- name: external_exports.string().min(1),
4596
- label: external_exports.string().min(1),
4597
- inputType: external_exports.enum(["text", "number", "date", "slug"]),
4598
- required: external_exports.boolean().default(true),
4599
- helperText: external_exports.string().min(1),
4600
- example: external_exports.string().min(1),
4601
- defaultValue: external_exports.string().optional()
4602
- }).strict();
4603
- var TemplateInputSchema = external_exports.object({
4604
- fields: external_exports.array(TemplateInputFieldSchema).min(1)
4605
- }).strict();
4606
- var TemplateDescriptorSchema = external_exports.object({
4607
- templateRef: external_exports.string().min(1),
4608
- vertical: external_exports.string().min(1),
4609
- description: external_exports.string().default(""),
4610
- inputSchema: TemplateInputSchema.optional()
4611
- }).strict();
4612
- var StandupDryRunPlanSchema = external_exports.object({
4613
- planOnly: external_exports.literal(true),
4614
- planOnlyMessage: external_exports.string().min(1),
4615
- product: external_exports.object({
4616
- studioId: external_exports.string().min(1),
4617
- productId: external_exports.string().min(1),
4618
- name: external_exports.string().min(1),
4619
- slug: external_exports.string().min(1),
4620
- vertical: external_exports.string().min(1)
4621
- }).strict(),
4622
- targetRepo: external_exports.object({
4623
- owner: external_exports.string().min(1),
4624
- name: external_exports.string().min(1),
4625
- fullName: external_exports.string().min(1),
4626
- defaultBranch: external_exports.string().min(1),
4627
- plannedState: external_exports.literal("would_create"),
4628
- exists: external_exports.literal(false)
4629
- }).strict(),
4630
- template: TemplateDescriptorSchema,
4631
- scaffold: external_exports.object({
4632
- label: external_exports.literal("scaffold (template output)"),
4633
- files: ScaffoldManifestSchema
4634
- }).strict(),
4635
- buildAgentSeed: external_exports.object({
4636
- label: external_exports.literal("build-agent instructions (not yet run)"),
4637
- instructions: external_exports.array(external_exports.string().min(1)).min(1),
4638
- product: external_exports.object({
4639
- name: external_exports.string().min(1),
4640
- slug: external_exports.string().min(1),
4641
- vertical: external_exports.string().min(1)
4642
- }).strict(),
4643
- repoFullName: external_exports.string().min(1)
4644
- }).strict(),
4645
- safetyEnvelope: external_exports.object({
4646
- estimatedCostUsd: external_exports.number().finite().nonnegative(),
4647
- costCapUsd: external_exports.number().finite().nonnegative(),
4648
- networkPolicy: external_exports.object({
4649
- mode: external_exports.literal("restricted"),
4650
- allowedHosts: external_exports.array(external_exports.string().min(1)).min(1)
4651
- }).strict(),
4652
- scopedToken: external_exports.object({
4653
- tokenMinted: external_exports.literal(false),
4654
- scope: external_exports.string().min(1),
4655
- ttlSeconds: external_exports.number().int().positive()
4656
- }).strict()
4657
- }).strict()
4658
- }).strict();
4659
- var ConstructionWorkflowArtifactKindSchema = external_exports.enum([
4660
- "profile",
4661
- "milestone_schedule",
4662
- "risk_register",
4663
- "submittal_register",
4664
- "long_lead_log",
4665
- "rfi_log",
4666
- "responsibility_matrix"
4667
- ]);
4668
- var IsoDateSchema = external_exports.string().regex(/^\d{4}-\d{2}-\d{2}$/);
4669
- var ConstructionWorkflowTemplateDescriptorSchema = external_exports.object({
4670
- templateRef: external_exports.string().min(1),
4671
- workflowKind: external_exports.literal("construction_project"),
4672
- templateKind: external_exports.literal("workflow_documents"),
4673
- name: external_exports.string().min(1),
4674
- description: external_exports.string().default(""),
4675
- artifacts: external_exports.array(ConstructionWorkflowArtifactKindSchema).min(1),
4676
- inputSchema: TemplateInputSchema
4677
- }).strict();
4678
- var ConstructionProjectSeedSchema = external_exports.object({
4679
- projectName: external_exports.string().min(1).max(120),
4680
- areaSqFt: external_exports.number().int().positive(),
4681
- projectType: external_exports.string().min(1).max(120),
4682
- buildingName: external_exports.string().min(1).max(160),
4683
- ntpDate: IsoDateSchema,
4684
- scheduleTargetDate: IsoDateSchema
4685
- }).strict();
4686
- var ConstructionMilestoneSchema = external_exports.object({
4687
- id: external_exports.string().min(1),
4688
- name: external_exports.string().min(1),
4689
- targetDate: IsoDateSchema,
4690
- status: external_exports.enum(["planned", "at_risk", "slipped", "complete"])
4691
- }).strict();
4692
- var ConstructionSubmittalSchema = external_exports.object({
4693
- id: external_exports.string().min(1),
4694
- item: external_exports.string().min(1),
4695
- division: external_exports.string().min(1),
4696
- needByDate: IsoDateSchema,
4697
- status: external_exports.enum(["not_started", "open", "in_review", "approved", "done"])
4698
- }).strict();
4699
- var ConstructionRfiSchema = external_exports.object({
4700
- id: external_exports.string().min(1),
4701
- subject: external_exports.string().min(1),
4702
- to: external_exports.string().min(1),
4703
- status: external_exports.enum(["draft", "open", "answered", "closed"]),
4704
- openedDate: IsoDateSchema
4705
- }).strict();
4706
- var ConstructionRiskSchema = external_exports.object({
4707
- id: external_exports.string().min(1),
4708
- risk: external_exports.string().min(1),
4709
- rating: external_exports.enum(["low", "medium", "high"]),
4710
- mitigation: external_exports.string().min(1),
4711
- confidence: external_exports.number().min(0).max(1)
4712
- }).strict();
4713
- var ConstructionLongLeadItemSchema = external_exports.object({
4714
- id: external_exports.string().min(1),
4715
- item: external_exports.string().min(1),
4716
- needByDate: IsoDateSchema,
4717
- status: external_exports.enum(["tracking", "ordered", "received", "done"]),
4718
- assumption: external_exports.string().min(1)
4719
- }).strict();
4720
- var ConstructionResponsibilitySchema = external_exports.object({
4721
- id: external_exports.string().min(1),
4722
- role: external_exports.string().min(1),
4723
- owner: external_exports.string().min(1),
4724
- responsibility: external_exports.string().min(1)
4725
- }).strict();
4726
- var ConstructionMarkdownArtifactSchema = external_exports.object({
4727
- kind: ConstructionWorkflowArtifactKindSchema,
4728
- path: external_exports.string().min(1),
4729
- markdown: external_exports.string().min(1)
4730
- }).strict();
4731
- var ConstructionWorkflowArtifactSetSchema = external_exports.object({
4732
- projectName: external_exports.string().min(1),
4733
- generatedAt: external_exports.string().datetime(),
4734
- assumptions: external_exports.array(external_exports.string().min(1)).default([]),
4735
- needsPmData: external_exports.array(external_exports.string().min(1)).default([]),
4736
- markdownArtifacts: external_exports.array(ConstructionMarkdownArtifactSchema).min(1),
4737
- structured: external_exports.object({
4738
- milestones: external_exports.array(ConstructionMilestoneSchema),
4739
- submittals: external_exports.array(ConstructionSubmittalSchema),
4740
- rfis: external_exports.array(ConstructionRfiSchema),
4741
- risks: external_exports.array(ConstructionRiskSchema),
4742
- longLeadItems: external_exports.array(ConstructionLongLeadItemSchema),
4743
- responsibilities: external_exports.array(ConstructionResponsibilitySchema)
4744
- }).strict()
4745
- }).strict();
4746
- var ConstructionWorkflowDryRunPlanSchema = external_exports.object({
4747
- planOnly: external_exports.literal(true),
4748
- planOnlyMessage: external_exports.string().min(1),
4749
- product: external_exports.object({
4750
- studioId: external_exports.string().min(1),
4751
- productId: external_exports.string().min(1),
4752
- name: external_exports.string().min(1),
4753
- vertical: external_exports.string().min(1)
4754
- }).strict(),
4755
- template: ConstructionWorkflowTemplateDescriptorSchema,
4756
- seed: ConstructionProjectSeedSchema,
4757
- safetyEnvelope: external_exports.object({
4758
- executor: external_exports.literal("benign_workflow_populator"),
4759
- sandboxUsed: external_exports.literal(false),
4760
- scopedTokenMinted: external_exports.literal(false),
4761
- externalWritesAllowed: external_exports.literal(false),
4762
- workspaceWriteMode: external_exports.literal("markdown_only")
4763
- }).strict()
4764
- }).strict();
4765
-
4766
- // ../shared/src/types/construction-log-excel.ts
4767
- var CONSTRUCTION_LOG_EXCEL_SCHEMA_VERSION = "construction-log-excel-v1";
4768
- var ConstructionLogExcelSheetKeySchema = external_exports.enum([
4769
- "submittals",
4770
- "rfis",
4771
- "riskRegister",
4772
- "longLead",
4773
- "responsibilityMatrix",
4774
- "milestones"
4775
- ]);
4776
- var ConstructionLogExcelColumnSchema = external_exports.object({
4777
- key: external_exports.string().min(1),
4778
- header: external_exports.string().min(1),
4779
- required: external_exports.boolean(),
4780
- description: external_exports.string().min(1)
4781
- }).strict().describe("Canonical column definition for Alfred construction log Excel round-trips.");
4782
- var ConstructionLogExcelSheetSchema = external_exports.object({
4783
- key: ConstructionLogExcelSheetKeySchema,
4784
- sheetName: external_exports.string().min(1),
4785
- description: external_exports.string().min(1),
4786
- columns: external_exports.array(ConstructionLogExcelColumnSchema).min(1)
4787
- }).strict().describe("Canonical worksheet definition for Alfred construction log Excel round-trips.");
4788
- var ConstructionLogExcelWorkbookSchema = external_exports.object({
4789
- schemaVersion: external_exports.literal(CONSTRUCTION_LOG_EXCEL_SCHEMA_VERSION),
4790
- sheets: external_exports.record(ConstructionLogExcelSheetKeySchema, ConstructionLogExcelSheetSchema)
4791
- }).strict().describe(
4792
- "Canonical Alfred construction log Excel workbook schema shared by native output generation and export-upload ingestion."
4793
- );
4794
- var CONSTRUCTION_LOG_EXCEL_SHEETS = {
4795
- submittals: {
4796
- key: "submittals",
4797
- sheetName: "Submittals",
4798
- description: "Submittal register rows generated by Alfred or edited by the PM.",
4799
- columns: [
4800
- column("id", "ID", true, "Stable submittal identifier, for example SUB-001."),
4801
- column("item", "Item", true, "Submittal item or package name."),
4802
- column("division", "Division", true, "Spec division or trade grouping."),
4803
- column("needByDate", "Need By Date", true, "Date needed in YYYY-MM-DD format."),
4804
- column("status", "Status", true, "One of not_started, open, in_review, approved, or done."),
4805
- commonColumn("assumptionsNotes")
4806
- ]
4807
- },
4808
- rfis: {
4809
- key: "rfis",
4810
- sheetName: "RFIs",
4811
- description: "RFI log rows generated by Alfred or edited by the PM.",
4812
- columns: [
4813
- column("id", "ID", true, "Stable RFI identifier, for example RFI-001."),
4814
- column("subject", "Subject", true, "RFI subject."),
4815
- column("to", "To", true, "Responsible recipient or ball-in-court party."),
4816
- column("status", "Status", true, "One of draft, open, answered, or closed."),
4817
- column("openedDate", "Opened Date", true, "Date opened in YYYY-MM-DD format."),
4818
- commonColumn("assumptionsNotes")
4819
- ]
4820
- },
4821
- riskRegister: {
4822
- key: "riskRegister",
4823
- sheetName: "Risk Register",
4824
- description: "Risk register rows generated by Alfred or edited by the PM.",
4825
- columns: [
4826
- column("id", "ID", true, "Stable risk identifier, for example RISK-001."),
4827
- column("risk", "Risk", true, "Risk statement."),
4828
- column("rating", "Rating", true, "One of low, medium, or high."),
4829
- column("mitigation", "Mitigation", true, "Mitigation plan."),
4830
- column("confidence", "Confidence", true, "Confidence score from 0 to 1."),
4831
- commonColumn("assumptionsNotes")
4832
- ]
4833
- },
4834
- longLead: {
4835
- key: "longLead",
4836
- sheetName: "Long-Lead",
4837
- description: "Long-lead procurement rows generated by Alfred or edited by the PM.",
4838
- columns: [
4839
- column("id", "ID", true, "Stable long-lead identifier, for example LL-001."),
4840
- column("item", "Item", true, "Long-lead item name."),
4841
- column("needByDate", "Need By Date", true, "Date needed in YYYY-MM-DD format."),
4842
- column("status", "Status", true, "One of tracking, ordered, received, or done."),
4843
- column("assumption", "Assumption", true, "Procurement assumption behind this row."),
4844
- commonColumn("assumptionsNotes")
4845
- ]
4846
- },
4847
- responsibilityMatrix: {
4848
- key: "responsibilityMatrix",
4849
- sheetName: "Responsibility Matrix",
4850
- description: "Responsibility matrix rows generated by Alfred or edited by the PM.",
4851
- columns: [
4852
- column("id", "ID", true, "Stable responsibility identifier, for example RESP-001."),
4853
- column("role", "Role", true, "Role or party."),
4854
- column("owner", "Owner", true, "Named owner, or Needs PM input when unknown."),
4855
- column("responsibility", "Responsibility", true, "Responsibility statement."),
4856
- commonColumn("assumptionsNotes")
4857
- ]
4858
- },
4859
- milestones: {
4860
- key: "milestones",
4861
- sheetName: "Milestones",
4862
- description: "Milestone schedule rows used to generate the MS Project XML schedule.",
4863
- columns: [
4864
- column("id", "ID", true, "Stable milestone identifier, for example MS-001."),
4865
- column("name", "Name", true, "Milestone or task name."),
4866
- column("targetDate", "Target Date", true, "Target date in YYYY-MM-DD format."),
4867
- column("status", "Status", true, "One of planned, at_risk, slipped, or complete."),
4868
- column("predecessorId", "Predecessor ID", false, "Optional predecessor milestone ID."),
4869
- commonColumn("assumptionsNotes")
4870
- ]
4871
- }
4872
- };
4873
- var CONSTRUCTION_LOG_EXCEL_WORKBOOK_SCHEMA = ConstructionLogExcelWorkbookSchema.parse({
4874
- schemaVersion: CONSTRUCTION_LOG_EXCEL_SCHEMA_VERSION,
4875
- sheets: CONSTRUCTION_LOG_EXCEL_SHEETS
4876
- });
4877
- function column(key, header, required, description) {
4878
- return { key, header, required, description };
4879
- }
4880
- function commonColumn(key) {
4881
- return column(
4882
- key,
4883
- "Assumptions / Notes",
4884
- false,
4885
- "Show-your-work note, including generated assumptions and PM-input gaps."
4886
- );
4887
- }
4888
-
4889
- // ../shared/src/types/dev-task-dispatch.ts
4890
- var CodingAgentExecutorSchema = external_exports.enum(["claude-code", "codex"]);
4891
- var DevTaskDispatchRequestSchema = external_exports.object({
4892
- studioId: external_exports.string().uuid(),
4893
- productId: external_exports.string().uuid(),
4894
- repo: RepoRefSchema,
4895
- task: external_exports.string().min(1).max(2e4),
4896
- executor: CodingAgentExecutorSchema
4897
- }).strict();
4898
- var DevTaskDispatchDryRunPlanSchema = external_exports.object({
4899
- planOnly: external_exports.literal(true),
4900
- planOnlyMessage: external_exports.string().min(1),
4901
- targetRepo: RepoRefSchema,
4902
- task: external_exports.string().min(1),
4903
- executor: CodingAgentExecutorSchema,
4904
- branchName: external_exports.string().min(1),
4905
- safetyEnvelope: external_exports.object({
4906
- estimatedCostUsd: external_exports.number().finite().nonnegative(),
4907
- costCapUsd: external_exports.number().finite().nonnegative(),
4908
- timeoutMs: external_exports.number().int().positive(),
4909
- scopedToken: external_exports.object({
4910
- tokenMinted: external_exports.literal(false),
4911
- scope: external_exports.string().min(1),
4912
- ttlSeconds: external_exports.number().int().positive()
4913
- }).strict(),
4914
- prOnly: external_exports.object({
4915
- opensPullRequest: external_exports.literal(true),
4916
- mergesPullRequest: external_exports.literal(false),
4917
- pushesMain: external_exports.literal(false),
4918
- deploys: external_exports.literal(false)
4919
- }).strict()
4920
- }).strict()
4921
- }).strict();
4922
- var CodingAgentRunInputSchema = external_exports.object({
4923
- executor: CodingAgentExecutorSchema,
4924
- repo: RepoRefSchema,
4925
- task: external_exports.string().min(1),
4926
- scopedToken: ScopedTokenSchema,
4927
- branchName: external_exports.string().min(1),
4928
- costCapUsd: external_exports.number().finite().nonnegative(),
4929
- timeoutMs: external_exports.number().int().positive()
4930
- }).strict();
4931
- var CodingAgentRunResultSchema = external_exports.discriminatedUnion("status", [
4932
- external_exports.object({
4933
- status: external_exports.literal("succeeded"),
4934
- prUrl: external_exports.string().url(),
4935
- summary: external_exports.string().min(1),
4936
- costUsd: external_exports.number().finite().nonnegative(),
4937
- /**
4938
- * The exact commit sha the PR branch was pushed at when it opened —
4939
- * captured server-side (see server-dispatch-backend.ts) right after a
4940
- * successful run, before the workspace is torn down. Lets the Maeve
4941
- * in-flight-fix detector (maeve-in-flight-pr-fix-lesson.ts) key off the
4942
- * real PR-open head instead of falling back to timestamp matching.
4943
- */
4944
- openedHeadSha: external_exports.string().min(1).optional()
4945
- }).strict(),
4946
- external_exports.object({
4947
- status: external_exports.literal("failed"),
4948
- summary: external_exports.string().min(1),
4949
- reason: external_exports.string().min(1),
4950
- costUsd: external_exports.number().finite().nonnegative().optional()
4951
- }).strict()
4952
- ]);
4953
- var DevTaskOutcomeSchema = external_exports.enum(["ci_passed", "pr_merged", "ci_failed"]);
4954
- var SecurityFindingClassSchema = external_exports.enum(["authz", "csrf", "injection", "secrets", "ssrf"]);
4955
- var RecordDevTaskOutcomeInputSchema = external_exports.object({
4956
- product: external_exports.string().min(1).max(120),
4957
- repo: external_exports.string().min(1).max(240),
4958
- prUrl: external_exports.string().url(),
4959
- outcome: DevTaskOutcomeSchema,
4960
- task: external_exports.string().min(1).max(2e4).optional(),
4961
- executor: CodingAgentExecutorSchema.optional(),
4962
- occurredAt: external_exports.string().datetime().optional(),
4963
- maeveLessonStatement: external_exports.string().min(1).max(1e3).optional(),
4964
- maeveLessonTags: external_exports.array(external_exports.string().min(1).max(120)).optional(),
4965
- /** Security metadata — enriches the Maeve lesson with class/pattern, never raw vulnerable detail. */
4966
- findingClass: SecurityFindingClassSchema.optional(),
4967
- ruleId: external_exports.string().min(1).max(120).optional(),
4968
- signalSource: external_exports.string().min(1).max(240).optional()
4969
- }).strict();
4970
-
4971
- // ../shared/src/schemas/standup-plan.ts
4972
- var StandupRequestSchema = external_exports.object({
4973
- productName: external_exports.string().min(1).max(80),
4974
- slug: external_exports.string().min(1).optional(),
4975
- vertical: external_exports.string().min(1).max(80),
4976
- repoTarget: external_exports.string().min(1).default("barg-labs"),
4977
- repoName: external_exports.string().min(1).optional(),
4978
- templateRef: external_exports.string().min(1).optional(),
4979
- scopeNotes: external_exports.string().max(2e3).optional()
4980
- }).strict();
4981
- var StandupPlanSchema = external_exports.object({
4982
- productName: external_exports.string().min(1).max(80),
4983
- slug: external_exports.string().regex(/^[a-z0-9][a-z0-9-]*[a-z0-9]$/),
4984
- vertical: external_exports.string().min(1).max(80),
4985
- templateRef: external_exports.string().min(1),
4986
- repoTarget: external_exports.string().min(1),
4987
- repoName: external_exports.string().regex(/^[a-z0-9][a-z0-9-]*[a-z0-9]$/),
4988
- fileManifest: external_exports.array(external_exports.string().min(1)).min(1),
4989
- credentialScope: external_exports.string().min(1),
4990
- estimatedCostUsd: external_exports.number().nonnegative(),
4991
- steps: external_exports.array(external_exports.string().min(1)).min(1),
4992
- dryRun: external_exports.literal(true)
4993
- }).strict();
4994
-
4995
- // ../shared/src/types/coordinator-prompt.ts
4996
- var CoordinatorPromptContextBlockSchema = external_exports.object({
4997
- title: external_exports.string().min(1).max(120),
4998
- body: external_exports.string().min(1).max(6e3),
4999
- source: external_exports.string().max(500).optional()
5000
- });
5001
- var CoordinatorPromptInputPayloadSchema = external_exports.object({
5002
- objective: external_exports.string().min(1).max(4e3),
5003
- productId: external_exports.string().min(1),
5004
- context: external_exports.array(CoordinatorPromptContextBlockSchema).min(1).max(20),
5005
- escalationHints: external_exports.array(external_exports.string().min(1).max(500)).max(10).optional()
5006
- });
5007
- var CoordinatorPromptTokensUsedSchema = external_exports.object({
5008
- input: external_exports.number().int().nonnegative(),
5009
- output: external_exports.number().int().nonnegative(),
5010
- total: external_exports.number().int().nonnegative(),
5011
- costCents: external_exports.number().nonnegative()
5012
- });
5013
- var CoordinatorPromptSchema = external_exports.object({
5014
- id: external_exports.string().uuid(),
5015
- studioId: external_exports.string().min(1),
5016
- productId: external_exports.string().min(1),
5017
- draftedAt: external_exports.coerce.date(),
5018
- inputPayload: CoordinatorPromptInputPayloadSchema,
5019
- markdown: external_exports.string().min(1),
5020
- metadata: external_exports.object({
5021
- tokensUsed: CoordinatorPromptTokensUsedSchema.optional(),
5022
- model: external_exports.string().optional(),
5023
- templateVersion: external_exports.string().optional()
5024
- }).catchall(external_exports.unknown()).optional()
5025
- });
5026
- var CreateCoordinatorPromptInputSchema = external_exports.object({
5027
- productId: external_exports.string().min(1),
5028
- inputPayload: CoordinatorPromptInputPayloadSchema,
5029
- markdown: external_exports.string().min(1),
5030
- metadata: external_exports.record(external_exports.unknown()).optional(),
5031
- draftedAt: external_exports.coerce.date().optional()
5032
- });
5033
- var ListCoordinatorPromptsInputSchema = external_exports.object({
5034
- productId: external_exports.string().min(1).optional(),
5035
- since: external_exports.coerce.date().optional()
5036
- });
5037
-
5038
- // ../shared/src/schemas/inbox-triage.ts
5039
- var InboxTriageClassificationSchema = external_exports.enum([
5040
- "needs_reply",
5041
- "fyi",
5042
- "waiting",
5043
- "escalate"
5044
- ]);
5045
- var InboxTriageLegacyUrgencySchema = external_exports.enum(["needs_reply", "fyi", "noise", "escalation"]);
5046
- var InboxTriageThreadSchema = external_exports.object({
5047
- id: external_exports.string().min(1),
5048
- subject: external_exports.string().min(1),
5049
- from: external_exports.string(),
5050
- to: external_exports.string(),
5051
- snippet: external_exports.string(),
5052
- labels: external_exports.array(external_exports.string()),
5053
- unread: external_exports.boolean(),
5054
- needsReply: external_exports.boolean(),
5055
- updatedAt: external_exports.string().min(1),
5056
- url: external_exports.string().min(1),
5057
- messageCount: external_exports.number().int().nonnegative()
5058
- });
5059
- var InboxTriageResultSchema = external_exports.object({
5060
- threadId: external_exports.string().min(1),
5061
- classification: InboxTriageClassificationSchema,
5062
- confidence: external_exports.number().min(0).max(1),
5063
- reason: external_exports.string(),
5064
- labelName: external_exports.string(),
5065
- applied: external_exports.boolean(),
5066
- error: external_exports.string().optional()
5067
- });
5068
- var TriageInboxUsageSchema = external_exports.object({
5069
- input_tokens: external_exports.number().int().nonnegative(),
5070
- output_tokens: external_exports.number().int().nonnegative(),
5071
- cached_tokens: external_exports.number().int().nonnegative().optional(),
5072
- cost_cents: external_exports.number().nonnegative()
5073
- });
5074
- var TriageInboxResultSchema = external_exports.object({
5075
- productId: external_exports.string().min(1),
5076
- results: external_exports.array(InboxTriageResultSchema),
5077
- usage: TriageInboxUsageSchema.optional()
5078
- });
5079
-
5080
- // ../shared/src/schemas/inference-usage.ts
5081
- var InferenceUsageSurfaceSchema = external_exports.string().min(1).max(80).regex(/^[a-z][a-z0-9_-]*$/);
5082
- var RecordInferenceUsageInputSchema = external_exports.object({
5083
- product: external_exports.string().min(1).optional(),
5084
- surface: InferenceUsageSurfaceSchema,
5085
- model: external_exports.string().min(1).max(120),
5086
- inputTokens: external_exports.number().int().nonnegative(),
5087
- outputTokens: external_exports.number().int().nonnegative(),
5088
- cachedTokens: external_exports.number().int().nonnegative().default(0),
5089
- costCents: external_exports.number().nonnegative(),
5090
- timestamp: external_exports.coerce.date().optional()
5091
- });
5092
- var InferenceUsageBreakdownQuerySchema = external_exports.object({
5093
- from: external_exports.coerce.date(),
5094
- to: external_exports.coerce.date()
5095
- });
5096
- var InferenceUsageGroupSchema = external_exports.object({
5097
- calls: external_exports.number().int().nonnegative(),
5098
- costCents: external_exports.number().nonnegative(),
5099
- inputTokens: external_exports.number().int().nonnegative(),
5100
- outputTokens: external_exports.number().int().nonnegative(),
5101
- cachedTokens: external_exports.number().int().nonnegative()
5102
- });
5103
- var InferenceUsageBreakdownSchema = external_exports.object({
5104
- from: external_exports.string().datetime(),
5105
- to: external_exports.string().datetime(),
5106
- totals: InferenceUsageGroupSchema,
5107
- bySurface: external_exports.array(InferenceUsageGroupSchema.extend({ surface: InferenceUsageSurfaceSchema })),
5108
- byModel: external_exports.array(InferenceUsageGroupSchema.extend({ model: external_exports.string().min(1) }))
5109
- });
5110
-
5111
- // ../shared/src/schemas/product-health.ts
5112
- var DEFAULT_PRODUCT_HEALTH_INTERVAL_SECONDS = 24 * 60 * 60;
5113
- var ISO_DATE_STRING = external_exports.string().datetime({ offset: true }).describe("ISO-8601 timestamp with timezone offset.");
5114
- var ProductHealthStatusSchema = external_exports.enum(["healthy", "degraded", "halted"]);
5115
- var ProductHealthDetailsSchema = external_exports.record(external_exports.unknown()).superRefine((details, ctx) => {
5116
- const credentialPath = findCredentialLikePath(details);
5117
- if (!credentialPath) return;
5118
- ctx.addIssue({
5119
- code: external_exports.ZodIssueCode.custom,
5120
- message: `Product health details must not contain credentials (${credentialPath}).`
5121
- });
5122
- });
5123
- var ProductHealthReportInputSchema = external_exports.object({
5124
- productId: external_exports.string().min(1).max(120),
5125
- status: ProductHealthStatusSchema,
5126
- lastActivityAt: ISO_DATE_STRING,
5127
- summary: external_exports.string().min(1).max(1e3),
5128
- details: ProductHealthDetailsSchema.optional(),
5129
- reportedAt: ISO_DATE_STRING,
5130
- expectedIntervalSeconds: external_exports.number().int().positive().optional()
5131
- });
5132
- var StoredProductHealthReportSchema = ProductHealthReportInputSchema.extend({
5133
- expectedIntervalSeconds: external_exports.number().int().positive()
5134
- });
5135
- var ProductLivenessStateSchema = external_exports.enum([
5136
- "healthy",
5137
- "degraded",
5138
- "halted",
5139
- "stale",
5140
- "unknown"
5141
- ]);
5142
- var ProductLivenessSnapshotEntrySchema = external_exports.object({
5143
- productId: external_exports.string().min(1),
5144
- state: ProductLivenessStateSchema,
5145
- flagged: external_exports.boolean(),
5146
- status: ProductHealthStatusSchema.optional(),
5147
- lastActivityAt: ISO_DATE_STRING.optional(),
5148
- reportedAt: ISO_DATE_STRING.optional(),
5149
- expectedIntervalSeconds: external_exports.number().int().positive(),
5150
- ageSeconds: external_exports.number().int().nonnegative().nullable(),
5151
- summary: external_exports.string()
5152
- });
5153
- function findCredentialLikePath(value, path = []) {
5154
- if (!value || typeof value !== "object") return null;
5155
- if (Array.isArray(value)) {
5156
- for (const [index, item] of value.entries()) {
5157
- const match = findCredentialLikePath(item, [...path, String(index)]);
5158
- if (match) return match;
5159
- }
5160
- return null;
5161
- }
5162
- for (const [key, nested] of Object.entries(value)) {
5163
- const nextPath = [...path, key];
5164
- if (/(?:secret|token|password|credential|api[-_]?key|private[-_]?key)/i.test(key)) {
5165
- return nextPath.join(".");
5166
- }
5167
- const match = findCredentialLikePath(nested, nextPath);
5168
- if (match) return match;
5169
- }
5170
- return null;
5171
- }
5172
-
5173
- // ../shared/src/schemas/interaction-trace.ts
5174
- var InteractionTraceVerificationSignalSchema = external_exports.enum([
5175
- "no_signal",
5176
- "human_accepted_output",
5177
- "human_rejected_output",
5178
- "ci_pr_succeeded",
5179
- "ci_pr_failed",
5180
- "brief_accepted",
5181
- "brief_rejected",
5182
- "standup_completed",
5183
- "standup_failed"
5184
- ]);
5185
- var InteractionTraceVerificationSchema = external_exports.object({
5186
- success: external_exports.boolean(),
5187
- signal: InteractionTraceVerificationSignalSchema,
5188
- confidence: external_exports.number().min(0).max(1),
5189
- reason: external_exports.string().min(1).max(1e3)
5190
- });
5191
- var InteractionTraceActorSchema = external_exports.object({
5192
- type: external_exports.enum(["human", "agent", "system"]),
5193
- id: external_exports.string().min(1).max(200),
5194
- name: external_exports.string().min(1).max(200).optional()
5195
- });
5196
- var RecordInteractionTraceInputSchema = external_exports.object({
5197
- product: external_exports.string().min(1).max(120),
5198
- intent: external_exports.string().min(1).max(500),
5199
- actionSummary: external_exports.string().min(1).max(4e3),
5200
- outcomeSummary: external_exports.string().min(1).max(4e3),
5201
- model: external_exports.string().min(1).max(200).nullable().optional(),
5202
- actor: InteractionTraceActorSchema,
5203
- occurredAt: external_exports.string().datetime().optional(),
5204
- verification: InteractionTraceVerificationSchema.optional(),
5205
- metadata: external_exports.record(external_exports.unknown()).optional()
5206
- });
5207
- var StoredInteractionTraceSchema = RecordInteractionTraceInputSchema.extend({
5208
- id: external_exports.string().uuid(),
5209
- occurredAt: external_exports.string().datetime(),
5210
- createdAt: external_exports.string().datetime(),
5211
- verification: InteractionTraceVerificationSchema
5212
- });
5213
- var InteractionTraceQualityScoreSchema = external_exports.number().min(0).max(1);
5214
- var RetrieveRelevantTracesQuerySchema = external_exports.object({
5215
- product: external_exports.string().min(1).max(120),
5216
- intent: external_exports.string().min(1).max(500),
5217
- limit: external_exports.number().int().positive().max(10).optional()
5218
- });
5219
- var RetrievedInteractionTraceSchema = StoredInteractionTraceSchema.extend({
5220
- score: external_exports.number().min(0).max(1),
5221
- qualityScore: InteractionTraceQualityScoreSchema
5222
- });
5223
-
5224
- // ../shared/src/schemas/maeve-lesson.ts
5225
- var MaeveLessonStatusSchema = external_exports.enum(["candidate", "verified", "retired"]);
5226
- var MaeveLessonEvidenceSchema = external_exports.object({
5227
- source: external_exports.enum(["interaction_trace", "artifact"]),
5228
- traceId: external_exports.string().uuid().optional(),
5229
- artifact: external_exports.string().min(1).max(1e3).optional(),
5230
- summary: external_exports.string().min(1).max(1e3),
5231
- hash: external_exports.string().regex(/^sha256:[a-f0-9]{64}$/)
5232
- });
5233
- var MaeveLessonSchema = external_exports.object({
5234
- id: external_exports.string().uuid(),
5235
- product: external_exports.string().min(1).max(120),
5236
- statement: external_exports.string().min(1).max(1e3),
5237
- scope: external_exports.array(external_exports.string().min(1).max(120)).default([]),
5238
- tags: external_exports.array(external_exports.string().min(1).max(120)).default([]),
5239
- evidence: external_exports.array(MaeveLessonEvidenceSchema),
5240
- status: MaeveLessonStatusSchema,
5241
- createdAt: external_exports.string().datetime(),
5242
- lastSeenAt: external_exports.string().datetime()
5243
- });
5244
- var CreateMaeveLessonInputSchema = external_exports.object({
5245
- product: external_exports.string().min(1).max(120),
5246
- statement: external_exports.string().min(1).max(1e3),
5247
- scope: external_exports.array(external_exports.string().min(1).max(120)).default([]),
5248
- tags: external_exports.array(external_exports.string().min(1).max(120)).default([]),
5249
- evidence: external_exports.array(MaeveLessonEvidenceSchema).default([]),
5250
- status: MaeveLessonStatusSchema.default("candidate"),
5251
- lastSeenAt: external_exports.string().datetime().optional()
5252
- });
5253
- var PromoteMaeveLessonInputSchema = external_exports.object({
5254
- id: external_exports.string().uuid(),
5255
- status: MaeveLessonStatusSchema,
5256
- appendEvidence: external_exports.array(MaeveLessonEvidenceSchema).optional()
5257
- });
5258
- var RecallMaeveLessonsQuerySchema = external_exports.object({
5259
- product: external_exports.string().min(1).max(120).optional(),
5260
- taskType: external_exports.string().min(1).max(120).optional(),
5261
- tags: external_exports.array(external_exports.string().min(1).max(120)).default([]),
5262
- limit: external_exports.number().int().positive().max(10).default(5),
5263
- /**
5264
- * Free-text query for semantic (pgvector cosine) recall. When set and an
5265
- * EmbeddingProvider is configured, recallMaeveLessons embeds this text and
5266
- * retrieves by cosine similarity, with exact-tag matches as a boost.
5267
- * Falls back to exact-class matching when the provider is NoOp.
5268
- */
5269
- semanticQuery: external_exports.string().min(1).max(500).optional()
5270
- });
5271
- var MaeveLessonSeedAnchorSchema = external_exports.object({
5272
- commit: external_exports.string().regex(/^[0-9a-f]{40}$/i, "commit must be a full 40-character git SHA"),
5273
- pr: external_exports.number().int().positive().nullable(),
5274
- summary: external_exports.string().min(1).max(1e3)
5275
- });
5276
- var MaeveLessonSeedSchema = external_exports.object({
5277
- statement: external_exports.string().min(1).max(1e3),
5278
- scope: external_exports.array(external_exports.string().min(1).max(120)).default([]),
5279
- tags: external_exports.array(external_exports.string().min(1).max(120)).default([]),
5280
- anchors: external_exports.array(MaeveLessonSeedAnchorSchema).min(1),
5281
- lastSeenAt: external_exports.string().datetime()
5282
- });
5283
- var ReviewFindingSeveritySchema = external_exports.enum(["critical", "high", "medium", "low"]);
5284
- var ReviewFindingLessonInputSchema = external_exports.object({
5285
- studioId: external_exports.string().min(1),
5286
- findingStudioId: external_exports.string().min(1),
5287
- product: external_exports.string().min(1).max(120),
5288
- repository: external_exports.string().min(1).max(240),
5289
- pullRequestNumber: external_exports.number().int().positive(),
5290
- findingText: external_exports.string().min(1).max(4e3),
5291
- severity: ReviewFindingSeveritySchema,
5292
- reviewer: external_exports.string().min(1).max(120),
5293
- remediatingCommitSha: external_exports.string().min(4).max(64),
5294
- /** The durable, reusable rule distilled from the finding — NOT the finding text verbatim. */
5295
- lessonStatement: external_exports.string().min(1).max(1e3),
5296
- scope: external_exports.array(external_exports.string().min(1).max(120)).default([]),
5297
- tags: external_exports.array(external_exports.string().min(1).max(120)).default([]),
5298
- occurredAt: external_exports.string().datetime()
5299
- });
5300
-
5301
- // ../shared/src/schemas/operator-trace.ts
5302
- var TRACE_ACTORS = [
5303
- "human",
5304
- "cowork",
5305
- "claude-code",
5306
- "codex",
5307
- "goal-runner",
5308
- "ci"
5309
- ];
5310
- var TraceActorSchema = external_exports.enum(TRACE_ACTORS);
5311
- var TRACE_SOURCES = [
5312
- "shell",
5313
- "cowork",
5314
- "claude-code",
5315
- "codex",
5316
- "goal-runner",
5317
- "github"
5318
- ];
5319
- var TraceSourceSchema = external_exports.enum(TRACE_SOURCES);
5320
- var TraceProvenanceSchema = external_exports.object({
5321
- source: TraceSourceSchema,
5322
- /** Absolute path of the source file/dir, or the gh query for CI events. */
5323
- path: external_exports.string().min(1).max(1e3),
5324
- /** Line number, session id, or PR number locating the row inside the source. */
5325
- locator: external_exports.string().min(1).max(200).optional()
5326
- });
5327
- var TraceRecordSchema = external_exports.object({
5328
- t: external_exports.string().datetime(),
5329
- actor: TraceActorSchema,
5330
- action: external_exports.string().min(1).max(2e3),
5331
- target: external_exports.string().max(1e3).default(""),
5332
- outcome: external_exports.string().max(2e3).default(""),
5333
- product: external_exports.string().min(1).max(120).optional(),
5334
- provenance: TraceProvenanceSchema
5335
- });
5336
- var ShellRedactionSchema = external_exports.enum(["none", "secret", "unclassified"]);
5337
- var ShellTraceEntrySchema = external_exports.object({
5338
- ts: external_exports.string().datetime(),
5339
- cwd: external_exports.string().min(1).max(1e3),
5340
- command: external_exports.string().min(1).max(4e3),
5341
- exitCode: external_exports.number().int(),
5342
- shellSessionId: external_exports.string().min(1).max(200),
5343
- redaction: ShellRedactionSchema
5344
- });
5345
- var TraceSourceReportSchema = external_exports.discriminatedUnion("status", [
5346
- external_exports.object({
5347
- status: external_exports.literal("ok"),
5348
- source: TraceSourceSchema,
5349
- recordCount: external_exports.number().int().nonnegative(),
5350
- /** Files/entries present but skipped (unparseable, filtered) — named, not silent. */
5351
- skipped: external_exports.array(external_exports.string().min(1).max(500)).default([])
5352
- }),
5353
- external_exports.object({
5354
- status: external_exports.literal("dark"),
5355
- source: TraceSourceSchema,
5356
- reason: external_exports.string().min(1).max(500)
5357
- })
5358
- ]);
5359
- var OperatorTimelineSchema = external_exports.object({
5360
- records: external_exports.array(TraceRecordSchema),
5361
- sources: external_exports.array(TraceSourceReportSchema)
5362
- });
5363
-
5364
- // ../shared/src/schemas/witan.ts
4517
+ // src/witan/schemas.ts
5365
4518
  var WITAN_RUBRIC_VERSION_V1 = "witan-rubric-v1-2026-06-24";
5366
4519
  var WITAN_RUBRIC_VERSION_V2 = "witan-rubric-v2-2026-07-12";
5367
4520
  var WITAN_RUBRIC_VERSION_V3 = "witan-rubric-v3-2026-07-13";
@@ -5391,11 +4544,9 @@ var WITAN_TRADING_RUBRIC_V0_CRITERION_IDS = [
5391
4544
  "audit-completeness",
5392
4545
  "claim-reality"
5393
4546
  ];
5394
- var WITAN_QUANT_INTEGRITY_RUBRIC_V0_CRITERION_IDS = ["quant-integrity"];
5395
4547
  var WitanCriterionIdSchema = external_exports.enum([
5396
4548
  ...WITAN_CRITERION_IDS,
5397
- ...WITAN_TRADING_RUBRIC_V0_CRITERION_IDS,
5398
- ...WITAN_QUANT_INTEGRITY_RUBRIC_V0_CRITERION_IDS
4549
+ ...WITAN_TRADING_RUBRIC_V0_CRITERION_IDS
5399
4550
  ]);
5400
4551
  var WitanTradingCriterionIdSchema = external_exports.enum(WITAN_TRADING_RUBRIC_V0_CRITERION_IDS);
5401
4552
  var WitanCriterionCategorySchema = external_exports.enum([
@@ -5423,8 +4574,6 @@ var WitanEvidenceKindSchema = external_exports.enum([
5423
4574
  "commit",
5424
4575
  "coverage",
5425
4576
  "dependency_report",
5426
- "dispatch_log",
5427
- "maeve_trace",
5428
4577
  "prod_check",
5429
4578
  "pull_request",
5430
4579
  "repository",
@@ -5446,7 +4595,10 @@ var WitanEvidencePointerSchema = external_exports.object({
5446
4595
  label: external_exports.string().min(1).max(180),
5447
4596
  url: external_exports.string().url().optional(),
5448
4597
  path: external_exports.string().min(1).max(700).optional(),
5449
- line: external_exports.number().int().positive().optional(),
4598
+ // Explicit null means the finding is file-scoped and no real match position was measured —
4599
+ // never a fabricated line (e.g. `1`) standing in for a position the detector never found
4600
+ // (goal_cejel_a2_one_notion_of_production_code_2026-07-13).
4601
+ line: external_exports.number().int().positive().nullable().optional(),
5450
4602
  contentHash: external_exports.string().min(8).max(160).optional(),
5451
4603
  capturedAt: external_exports.string().datetime({ offset: true }).optional()
5452
4604
  }).strict().refine((value) => Boolean(value.url ?? value.path ?? value.contentHash), {
@@ -5558,981 +4710,124 @@ var WitanReportSchema = external_exports.object({
5558
4710
  archetype: WitanRepoArchetypeSchema.optional(),
5559
4711
  insufficientSourceReason: external_exports.string().min(1).max(2e3).optional()
5560
4712
  }).strict();
5561
-
5562
- // ../shared/src/schemas/work-item.ts
5563
- var WorkItemTypeSchema = external_exports.enum(["feature", "bug"]);
5564
- var WorkItemPrioritySchema = external_exports.enum(["low", "normal", "high", "urgent"]);
5565
- var WorkItemStatusSchema = external_exports.enum([
5566
- "submitted",
5567
- "scoped",
5568
- "dispatched",
5569
- "pr_open",
5570
- "done",
5571
- "declined"
5572
- ]);
5573
- var CreateWorkItemInputSchema = external_exports.object({
5574
- productId: external_exports.string().uuid(),
5575
- type: WorkItemTypeSchema,
5576
- title: external_exports.string().min(3).max(180),
5577
- description: external_exports.string().min(8).max(2e4),
5578
- acceptanceCriteria: external_exports.string().max(2e4).optional(),
5579
- priority: WorkItemPrioritySchema.default("normal")
5580
- }).strict();
5581
- var ScopeWorkItemInputSchema = external_exports.object({
5582
- scopedTask: external_exports.string().min(8).max(2e4).optional()
5583
- }).strict();
5584
- var ListWorkItemsQuerySchema = external_exports.object({
5585
- productId: external_exports.string().uuid().optional(),
5586
- status: WorkItemStatusSchema.optional()
5587
- }).strict();
5588
- var DispatchWorkItemInputSchema = external_exports.object({
5589
- executor: external_exports.enum(["claude-code", "codex"]).default("codex"),
5590
- mode: external_exports.enum(["dry-run", "execute"]).default("dry-run")
5591
- }).strict();
5592
-
5593
- // ../shared/src/schemas/goal-frontmatter.ts
5594
- var GoalStreamKindSchema = external_exports.enum(["code", "process"]);
5595
- var GoalPrioritySchema = external_exports.enum(["p0", "p1", "p2"]);
5596
- var GoalFrontmatterExtrasSchema = external_exports.object({
5597
- stream: external_exports.string().min(1).nullable().default(null),
5598
- order: external_exports.number().int().nullable().default(null),
5599
- dependsOn: external_exports.array(external_exports.string().min(1)).default([]),
5600
- priority: GoalPrioritySchema.nullable().default(null),
5601
- kind: GoalStreamKindSchema.default("code")
5602
- });
5603
-
5604
- // ../shared/src/schemas/stream.ts
5605
- var StreamSchema = external_exports.object({
5606
- id: external_exports.string().uuid(),
5607
- studioId: external_exports.string().uuid(),
5608
- name: external_exports.string().min(1).max(120),
5609
- tag: external_exports.string().max(60).nullable(),
5610
- kind: GoalStreamKindSchema,
5611
- orderIndex: external_exports.number().int(),
5612
- createdAt: external_exports.coerce.date(),
5613
- updatedAt: external_exports.coerce.date()
5614
- });
5615
- var StreamItemSchema = external_exports.object({
5616
- id: external_exports.string().uuid(),
5617
- studioId: external_exports.string().uuid(),
5618
- streamId: external_exports.string().uuid(),
5619
- orderIndex: external_exports.number().int(),
5620
- title: external_exports.string().min(1).max(200),
5621
- /** docs/orchestration/goal_*.md filename (no extension) for code items; null for process items. */
5622
- goalName: external_exports.string().min(1).nullable(),
5623
- refLabel: external_exports.string().max(60).nullable(),
5624
- /** Free-form governed-run prompt text (mirrors the prototype's per-item `run` string). Null = no run control shown. */
5625
- runPrompt: external_exports.string().min(1).nullable(),
5626
- createdAt: external_exports.coerce.date(),
5627
- updatedAt: external_exports.coerce.date()
5628
- });
5629
- var StreamItemDisplayStatusSchema = external_exports.enum([
5630
- "done",
5631
- "in-review",
5632
- "running",
5633
- "queued",
5634
- "blocked",
5635
- "local-unknown"
5636
- ]);
5637
-
5638
- // ../shared/src/schemas/runner-dispatch.ts
5639
- var RUNNER_DISPATCH_MODES = ["dry-run", "execute"];
5640
- var RunnerDispatchModeSchema = external_exports.enum(RUNNER_DISPATCH_MODES);
5641
- var RUNNER_DISPATCH_STATUSES = ["queued", "claimed", "running", "done", "failed"];
5642
- var RunnerDispatchStatusSchema = external_exports.enum(RUNNER_DISPATCH_STATUSES);
5643
- var GOAL_CARD_PATTERN = /^docs\/orchestration\/[A-Za-z0-9_./-]+\.md$/;
5644
- function isAllowedGoalCardPath(goalCard) {
5645
- if (!GOAL_CARD_PATTERN.test(goalCard)) return false;
5646
- return goalCard.split("/").every((segment) => segment !== "." && segment !== "..");
5647
- }
5648
- var GoalCardPathSchema = external_exports.string().min(1).max(300).refine(isAllowedGoalCardPath, { message: "goal_card_invalid" });
5649
- var RunnerDispatchRequestSchema = external_exports.object({
5650
- goalCard: GoalCardPathSchema,
5651
- stream: external_exports.string().min(1).max(120).optional(),
5652
- mode: RunnerDispatchModeSchema
5653
- });
5654
-
5655
- // ../shared/src/schemas/witan-metrics-manifest.ts
5656
- var WITAN_METRICS_MANIFEST_SCHEMA_VERSION = "witan-metrics-manifest-v0";
5657
- var WitanMetricsManifestReturnsFrequencySchema = external_exports.enum([
5658
- "daily",
5659
- "weekly",
5660
- "monthly",
5661
- "annual"
5662
- ]);
5663
- var WitanMetricsManifestFoldSchema = external_exports.object({
5664
- foldId: external_exports.string().min(1).max(80),
5665
- inSampleSharpe: external_exports.number().optional(),
5666
- outOfSampleSharpe: external_exports.number().optional()
5667
- }).strict();
5668
- var WitanMetricsManifestCscvTrialSchema = external_exports.object({
5669
- trialId: external_exports.string().min(1).max(80),
5670
- blockReturns: external_exports.array(external_exports.number()).min(2)
5671
- }).strict();
5672
- var WitanMetricsManifestCscvSchema = external_exports.object({
5673
- // Must be even (split into IS/OOS halves) — enforced by the grader, not the schema.
5674
- blocks: external_exports.number().int().min(4).max(16),
5675
- trials: external_exports.array(WitanMetricsManifestCscvTrialSchema).min(2).max(200)
5676
- }).strict();
5677
- var WitanMetricsManifestCostModelSchema = external_exports.object({
5678
- feeBps: external_exports.number().min(0).optional(),
5679
- slippageBps: external_exports.number().min(0).optional(),
5680
- borrowBps: external_exports.number().min(0).optional(),
5681
- notes: external_exports.string().min(1).max(300).optional()
5682
- }).strict();
5683
- var WitanMetricsManifestParameterPointSchema = external_exports.object({
5684
- // Human-readable label for this point (e.g. "72" or "72 bars") — evidence/display only.
5685
- paramLabel: external_exports.string().min(1).max(80),
5686
- // The point's position on its swept axis, used to find its nearest neighbors by distance.
5687
- paramValue: external_exports.number(),
5688
- outOfSampleSharpe: external_exports.number()
5689
- }).strict();
5690
- var WitanMetricsManifestParameterSweepSchema = external_exports.object({
5691
- // Name of the swept parameter (e.g. "lookback_bars") — evidence/display only.
5692
- paramName: external_exports.string().min(1).max(80),
5693
- points: external_exports.array(WitanMetricsManifestParameterPointSchema).min(3).max(500)
5694
- }).strict();
5695
- var WitanMetricsManifestLabelSourceSchema = external_exports.enum([
5696
- "real_forward_returns",
5697
- "synthetic",
5698
- "unknown"
5699
- ]);
5700
- var WitanMetricsManifestSchema = external_exports.object({
5701
- schemaVersion: external_exports.literal(WITAN_METRICS_MANIFEST_SCHEMA_VERSION),
5702
- strategyName: external_exports.string().min(1).max(200).optional(),
5703
- // The headline reported Sharpe ratio the target repo is claiming.
5704
- reportedSharpe: external_exports.number(),
5705
- // How many trials/backtests were run in the search that produced reportedSharpe (the
5706
- // "1-of-42" count) — required so the grader can correct for selection bias.
5707
- trialCount: external_exports.number().int().positive(),
5708
- // Track-record length in return observations (e.g. 252 for a year of daily returns) —
5709
- // the `n` in the Probabilistic/Deflated Sharpe Ratio formula.
5710
- trackRecordObservations: external_exports.number().int().positive(),
5711
- returnsFrequency: WitanMetricsManifestReturnsFrequencySchema.default("daily"),
5712
- // Skew/kurtosis of the returns distribution; default to the normal-distribution values
5713
- // (0 skew, kurtosis 3) when the repo does not report them.
5714
- skewness: external_exports.number().default(0),
5715
- kurtosis: external_exports.number().min(0).default(3),
5716
- // Whether reportedSharpe is net of trading costs (fees/slippage/borrow/roll).
5717
- netOfCosts: external_exports.boolean(),
5718
- costModel: WitanMetricsManifestCostModelSchema.optional(),
5719
- // Per-fold in-sample vs out-of-sample breakdown, when the repo reports one.
5720
- folds: external_exports.array(WitanMetricsManifestFoldSchema).default([]),
5721
- // Per-trial, per-block performance matrix for the CSCV/PBO computation, when available.
5722
- cscv: WitanMetricsManifestCscvSchema.optional(),
5723
- // Parameter-sweep breakdown for the run-tier (L3b) parameter-neighborhood robustness
5724
- // grader, when the run swept a parameter (e.g. a lookback window) and recorded OOS
5725
- // performance at each swept value.
5726
- parameterSweep: WitanMetricsManifestParameterSweepSchema.optional(),
5727
- // Provenance of the labels behind reportedSharpe (labelling-integrity, L1+artifact tier).
5728
- labelSource: WitanMetricsManifestLabelSourceSchema.optional()
5729
- }).strict();
5730
-
5731
- // ../shared/src/schemas/witan-strategy-adapter.ts
5732
- var WITAN_STRATEGY_ADAPTER_CONFIG_SCHEMA_VERSION = "witan-strategy-adapter-v0";
5733
- var WitanStrategyAdapterConfigSchema = external_exports.object({
5734
- schemaVersion: external_exports.literal(WITAN_STRATEGY_ADAPTER_CONFIG_SCHEMA_VERSION),
5735
- // Argv for the strategy entrypoint, e.g. ["python3", "strategy.py"] or ["node", "run.mjs"].
5736
- // Command-argv (not a language enum) is what keeps the adapter language-agnostic — most
5737
- // real targets are Python, but the contract does not assume it.
5738
- command: external_exports.array(external_exports.string().min(1).max(300)).min(1).max(20),
5739
- // Relative path (within the target repo) to the data the strategy should backtest against.
5740
- dataPath: external_exports.string().min(1).max(500).optional(),
5741
- // Backtest window, as the target repo defines its own date strings (ISO-8601 recommended).
5742
- // Optional — a strategy may declare its own default window instead.
5743
- windowStart: external_exports.string().min(1).max(40).optional(),
5744
- windowEnd: external_exports.string().min(1).max(40).optional(),
5745
- // Relative path (within the sandboxed workspace) the entrypoint must write its raw result
5746
- // to — see WitanStrategyRunResultSchema below.
5747
- outputPath: external_exports.string().min(1).max(300).default("witan-run-result.json"),
5748
- timeoutMs: external_exports.number().int().positive().max(30 * 60 * 1e3).default(2 * 60 * 1e3),
5749
- // Explicit opt-in egress allowlist. Empty by default — no network from the sandboxed run
5750
- // unless the target repo explicitly whitelists hosts here.
5751
- allowedHosts: external_exports.array(external_exports.string().min(1).max(255)).max(20).default([])
5752
- }).strict();
5753
- var WitanStrategyRunResultSchema = WitanMetricsManifestSchema.omit({
5754
- schemaVersion: true
5755
- });
5756
-
5757
- // ../shared/src/types/tactical-action.ts
5758
- var TacticalActionTypeSchema = external_exports.enum([
5759
- "merge_pr_auto_merge_safe",
5760
- "deploy_staging",
5761
- "acknowledge_canary_alert",
5762
- "update_status_md",
5763
- "provision_product",
5764
- "dispatch_dev_task"
5765
- ]);
5766
- var TacticalActionStatusSchema = external_exports.enum(["executed", "blocked", "dry_run"]);
5767
- var TacticalActionPolicySchema = external_exports.object({
5768
- studioId: external_exports.string().uuid(),
5769
- productId: external_exports.string().uuid(),
5770
- actionType: TacticalActionTypeSchema,
5771
- allowed: external_exports.boolean(),
5772
- dryRun: external_exports.boolean(),
5773
- promotedAt: external_exports.coerce.date().nullable(),
5774
- forceEnableReason: external_exports.string().nullable()
5775
- });
5776
- var BaseActionSchema = external_exports.object({
5777
- actionType: TacticalActionTypeSchema,
5778
- productId: external_exports.string().uuid(),
5779
- coordinatorSessionId: external_exports.string().uuid().nullable().optional(),
5780
- customerFacingProduction: external_exports.boolean().default(false)
5781
- });
5782
- var MergePrTacticalActionSchema = BaseActionSchema.extend({
5783
- actionType: external_exports.literal("merge_pr_auto_merge_safe"),
5784
- repository: external_exports.string().min(1),
5785
- pullRequestNumber: external_exports.number().int().positive(),
5786
- labels: external_exports.array(external_exports.string()),
5787
- ciStatus: external_exports.enum(["green", "red", "unknown"]),
5788
- humanApprovals: external_exports.number().int().nonnegative(),
5789
- coworkClaudeApprovedStatus: external_exports.enum(["green", "red", "unknown"]),
5790
- // The PR head SHA captured at the SAME live precondition snapshot that
5791
- // verified the label/CI/approvals/cowork-claude-approved gates. Threaded
5792
- // through to the GitHub merge call as the conditional `sha` parameter so a
5793
- // commit that lands between the snapshot and the merge (a fast follow-up
5794
- // push, or a re-triggered CI run resetting status) can never be
5795
- // squash-merged unverified — GitHub rejects the merge with 409 instead.
5796
- headSha: external_exports.string().min(1)
5797
- });
5798
- var DeployStagingTacticalActionSchema = BaseActionSchema.extend({
5799
- actionType: external_exports.literal("deploy_staging"),
5800
- environment: external_exports.literal("staging"),
5801
- mainStatus: external_exports.enum(["green", "red", "unknown"]),
5802
- stagingStatus: external_exports.enum(["green", "red", "unknown"])
5803
- });
5804
- var AcknowledgeCanaryAlertTacticalActionSchema = BaseActionSchema.extend({
5805
- actionType: external_exports.literal("acknowledge_canary_alert"),
5806
- alertId: external_exports.string().min(1),
5807
- fingerprint: external_exports.string().min(1),
5808
- knownFalsePositiveFingerprints: external_exports.array(external_exports.string()).default([])
5809
- });
5810
- var UpdateStatusMdTacticalActionSchema = BaseActionSchema.extend({
5811
- actionType: external_exports.literal("update_status_md"),
5812
- source: external_exports.literal("daily_brief_synthesis"),
5813
- statusMarkdown: external_exports.string().min(1).max(2e4)
5814
- });
5815
- var ProvisionProductTacticalActionSchema = BaseActionSchema.extend({
5816
- actionType: external_exports.literal("provision_product"),
5817
- productName: external_exports.string().min(1).max(80),
5818
- vertical: external_exports.string().min(1).max(80),
5819
- repoTarget: external_exports.string().min(1),
5820
- templateRef: external_exports.string().min(1),
5821
- scopeNotes: external_exports.string().max(2e3).optional()
5822
- });
5823
- var DispatchDevTaskTacticalActionSchema = BaseActionSchema.extend({
5824
- actionType: external_exports.literal("dispatch_dev_task"),
5825
- repo: RepoRefSchema,
5826
- task: external_exports.string().min(1).max(2e4),
5827
- executor: CodingAgentExecutorSchema
5828
- });
5829
- var TacticalActionSchema = external_exports.discriminatedUnion("actionType", [
5830
- MergePrTacticalActionSchema,
5831
- DeployStagingTacticalActionSchema,
5832
- AcknowledgeCanaryAlertTacticalActionSchema,
5833
- UpdateStatusMdTacticalActionSchema,
5834
- ProvisionProductTacticalActionSchema,
5835
- DispatchDevTaskTacticalActionSchema
5836
- ]);
5837
- var TacticalActionContextSchema = external_exports.object({
5838
- studioId: external_exports.string().uuid(),
5839
- actorUserId: external_exports.string().uuid().nullable().optional(),
5840
- requestedAt: external_exports.coerce.date().optional()
5841
- });
5842
- var TacticalActionPermitResultSchema = external_exports.discriminatedUnion("status", [
5843
- external_exports.object({
5844
- status: external_exports.literal("executed"),
5845
- auditLogId: external_exports.string().uuid(),
5846
- reason: external_exports.literal("permit_allowed")
5847
- }),
4713
+ var WITAN_ATTESTATION_STATEMENT_TYPE = "https://in-toto.io/Statement/v1";
4714
+ var WITAN_ATTESTATION_PREDICATE_TYPE = "https://cejel.dev/attestations/scan/v1";
4715
+ var WitanAttestationOutcomeSchema = external_exports.discriminatedUnion("status", [
5848
4716
  external_exports.object({
5849
- status: external_exports.literal("blocked"),
5850
- auditLogId: external_exports.string().uuid().optional(),
5851
- reason: external_exports.string().min(1)
5852
- }),
4717
+ status: external_exports.literal("scored"),
4718
+ overallScore: external_exports.number().min(0).max(4),
4719
+ codeTrustScore: external_exports.number().min(0).max(4),
4720
+ processTrustScore: external_exports.number().min(0).max(4)
4721
+ }).strict(),
5853
4722
  external_exports.object({
5854
- status: external_exports.literal("dry_run"),
5855
- auditLogId: external_exports.string().uuid(),
5856
- reason: external_exports.literal("dry_run_mode"),
5857
- wouldHaveDone: external_exports.record(external_exports.unknown())
5858
- })
5859
- ]);
5860
- var TacticalActionLogEntrySchema = external_exports.object({
5861
- id: external_exports.string().uuid(),
5862
- studioId: external_exports.string().uuid(),
5863
- productId: external_exports.string().uuid(),
5864
- product: external_exports.string().nullable().optional(),
5865
- coordinatorSessionId: external_exports.string().uuid().nullable(),
5866
- actionType: TacticalActionTypeSchema.or(external_exports.string()),
5867
- context: external_exports.record(external_exports.unknown()),
5868
- permitResult: external_exports.record(external_exports.unknown()),
5869
- status: TacticalActionStatusSchema,
5870
- outcome: external_exports.string().nullable(),
5871
- wouldHaveDone: external_exports.record(external_exports.unknown()).nullable(),
5872
- attemptedAt: external_exports.string(),
5873
- executedAt: external_exports.string().nullable()
5874
- });
5875
-
5876
- // ../shared/src/schemas/index.ts
5877
- var StudioSchema = external_exports.object({
5878
- id: external_exports.string().uuid(),
5879
- name: external_exports.string().min(1).max(100),
5880
- billingStatus: external_exports.enum(["trial", "active", "past_due", "cancelled"]),
5881
- planTier: external_exports.enum(["trial", "solo", "studio", "studio_plus", "self_hosted", "enterprise"]),
5882
- onPrem: external_exports.boolean().default(false),
5883
- createdAt: external_exports.coerce.date()
5884
- });
5885
- var HumanSchema = external_exports.object({
5886
- id: external_exports.string().uuid(),
5887
- studioId: external_exports.string().uuid(),
5888
- email: external_exports.string().email(),
5889
- name: external_exports.string().min(1).max(120),
5890
- oauthProviders: external_exports.array(external_exports.enum(["google", "microsoft", "apple"])).default([]),
5891
- role: external_exports.enum(["owner", "member", "advisor", "per_product"]),
5892
- timezone: external_exports.string(),
5893
- briefTime: external_exports.string().regex(/^\d{2}:\d{2}$/),
5894
- createdAt: external_exports.coerce.date()
5895
- });
5896
- var ProductSchema = external_exports.object({
5897
- id: external_exports.string().uuid(),
5898
- studioId: external_exports.string().uuid(),
5899
- name: external_exports.string().min(1).max(80),
5900
- slug: external_exports.string().regex(/^[a-z0-9][a-z0-9-]*[a-z0-9]$/),
5901
- status: external_exports.enum(["active", "snoozed", "wound_down", "deleted"]),
5902
- description: external_exports.string().max(280).optional(),
5903
- repoUrl: external_exports.string().url().optional(),
5904
- calendarTag: external_exports.string().optional(),
5905
- emailLabelPrefix: external_exports.string().optional(),
5906
- colorHex: external_exports.string().regex(/^#[0-9a-fA-F]{6}$/).optional(),
5907
- scheduleBriefTime: external_exports.string().regex(/^\d{2}:\d{2}$/).optional(),
5908
- briefTemplateId: external_exports.string().uuid().optional(),
5909
- regulated: external_exports.boolean().default(false),
5910
- createdAt: external_exports.coerce.date(),
5911
- lastTouchedAt: external_exports.coerce.date()
5912
- });
5913
- var AgentSchema = external_exports.object({
5914
- id: external_exports.string().uuid(),
5915
- studioId: external_exports.string().uuid(),
5916
- productId: external_exports.string().uuid(),
5917
- agentType: external_exports.enum(["codex", "claude-code", "cowork", "cursor", "cline", "aider", "other"]),
5918
- sessionId: external_exports.string().optional(),
5919
- status: external_exports.enum(["active", "idle", "registered", "archived"]),
5920
- registeredAt: external_exports.coerce.date(),
5921
- lastActiveAt: external_exports.coerce.date().optional(),
5922
- totalCostCentsLifetime: external_exports.number().int().nonnegative().default(0)
5923
- });
5924
- var AgentRunSchema = external_exports.object({
5925
- id: external_exports.string().uuid(),
5926
- agentId: external_exports.string().uuid(),
5927
- coordinatorSessionId: external_exports.string().uuid().nullable().optional(),
5928
- startedAt: external_exports.coerce.date(),
5929
- completedAt: external_exports.coerce.date().optional(),
5930
- actionType: external_exports.string(),
5931
- toolName: external_exports.string().optional(),
5932
- toolInputSummary: external_exports.string().optional(),
5933
- toolOutputSummary: external_exports.string().optional(),
5934
- tokensUsedInput: external_exports.number().int().nonnegative().default(0),
5935
- tokensUsedOutput: external_exports.number().int().nonnegative().default(0),
5936
- costCents: external_exports.number().int().nonnegative().default(0),
5937
- durationMs: external_exports.number().int().nonnegative().default(0),
5938
- resultStatus: external_exports.enum(["success", "failure", "partial", "timeout"]).optional(),
5939
- resultSummary: external_exports.string().optional(),
5940
- filesTouched: external_exports.array(external_exports.string()).default([])
5941
- });
5942
- var CoordinatorStatusSchema = external_exports.enum([
5943
- "draft",
5944
- "spawned",
5945
- "in_progress",
5946
- "reporting",
5947
- "closed"
4723
+ status: external_exports.literal("abstained"),
4724
+ reason: external_exports.string().min(1).max(2e3)
4725
+ }).strict()
5948
4726
  ]);
5949
- var CoordinatorEscalationPolicySchema = external_exports.object({
5950
- stuck_after_hours: external_exports.number().int().positive(),
5951
- method: external_exports.literal("flag_for_human"),
5952
- urgency: external_exports.enum(["low", "medium", "high", "critical"]).optional()
5953
- });
5954
- var CoordinatorSessionSchema = external_exports.object({
5955
- id: external_exports.string().uuid(),
5956
- studioId: external_exports.string().uuid(),
5957
- productId: external_exports.string().uuid(),
5958
- promptId: external_exports.string().uuid().nullable(),
5959
- objective: external_exports.string(),
5960
- status: CoordinatorStatusSchema,
5961
- spawnedAt: external_exports.coerce.date().nullable(),
5962
- closedAt: external_exports.coerce.date().nullable(),
5963
- escalationPolicy: CoordinatorEscalationPolicySchema.nullable(),
5964
- outcomeSummary: external_exports.string().nullable(),
5965
- createdAt: external_exports.coerce.date()
5966
- });
5967
- var AgentActivityWindowSchema = external_exports.enum(["24h", "7d", "30d"]);
5968
- var AgentCostBucketSchema = external_exports.object({
5969
- key: external_exports.string(),
5970
- name: external_exports.string(),
5971
- runCount: external_exports.number().int().nonnegative(),
5972
- costUsd: external_exports.number().nonnegative()
5973
- });
5974
- var AgentCostRollupSchema = external_exports.object({
5975
- window: AgentActivityWindowSchema,
5976
- studioTotalUsd: external_exports.number().nonnegative(),
5977
- runCount: external_exports.number().int().nonnegative(),
5978
- byAgent: external_exports.array(AgentCostBucketSchema),
5979
- byProduct: external_exports.array(AgentCostBucketSchema)
5980
- });
5981
- var AgentConflictRecordSchema = external_exports.object({
5982
- file: external_exports.string(),
5983
- agents: external_exports.array(external_exports.string()).min(2),
5984
- references: external_exports.array(
4727
+ var WitanAttestationStatementSchema = external_exports.object({
4728
+ _type: external_exports.literal(WITAN_ATTESTATION_STATEMENT_TYPE),
4729
+ subject: external_exports.array(
5985
4730
  external_exports.object({
5986
- runId: external_exports.string(),
5987
- agent: external_exports.string(),
5988
- product: external_exports.string().nullable(),
5989
- startedAt: external_exports.string(),
5990
- sessionRef: external_exports.string().nullable(),
5991
- prUrl: external_exports.string().nullable()
5992
- })
5993
- )
5994
- });
5995
- var AgentLeaderboardEntrySchema = external_exports.object({
5996
- agent: external_exports.string(),
5997
- product: external_exports.string().nullable(),
5998
- runCount: external_exports.number().int().nonnegative(),
5999
- completedRuns: external_exports.number().int().nonnegative(),
6000
- failedRuns: external_exports.number().int().nonnegative(),
6001
- costUsd: external_exports.number().nonnegative(),
6002
- filesTouched: external_exports.number().int().nonnegative(),
6003
- conflicts: external_exports.number().int().nonnegative(),
6004
- state: external_exports.enum(["productive", "idle", "duplicating"]),
6005
- lastActiveAt: external_exports.string().nullable()
6006
- });
6007
- var ModelCostEstimateInputSchema = external_exports.object({
6008
- model: external_exports.string().optional(),
6009
- inputTokens: external_exports.number().int().nonnegative().default(0),
6010
- outputTokens: external_exports.number().int().nonnegative().default(0)
6011
- });
6012
- var ModelCostEstimateSchema = external_exports.object({
6013
- costUsd: external_exports.number().nonnegative(),
6014
- method: external_exports.enum(["estimated_from_model_rate", "unknown_model_rate"]),
6015
- rateModel: external_exports.enum(["claude-haiku", "claude-sonnet", "claude-opus", "unknown"])
6016
- });
6017
- var IntegrationSchema = external_exports.object({
6018
- id: external_exports.string().uuid(),
6019
- studioId: external_exports.string().uuid(),
6020
- productId: external_exports.string().uuid().nullable(),
6021
- kind: external_exports.string(),
6022
- oauthTokenEncrypted: external_exports.string().optional(),
6023
- refreshTokenEncrypted: external_exports.string().optional(),
6024
- status: external_exports.enum(["active", "broken", "revoked"]),
6025
- lastSyncAt: external_exports.coerce.date().optional(),
6026
- errorCount: external_exports.number().int().nonnegative().default(0)
6027
- });
6028
- var EmailAccountSchema = external_exports.object({
6029
- id: external_exports.string().uuid(),
6030
- studioId: external_exports.string().uuid(),
6031
- provider: external_exports.enum(["gmail", "m365", "imap"]),
6032
- oauthTokenEncrypted: external_exports.string().optional(),
6033
- defaultLabelPrefix: external_exports.string().optional(),
6034
- triageCadenceMins: external_exports.number().int().positive().default(240)
6035
- });
6036
- var RoutineSchema = external_exports.object({
6037
- id: external_exports.string().uuid(),
6038
- productId: external_exports.string().uuid().nullable(),
6039
- name: external_exports.string(),
6040
- cronExpression: external_exports.string(),
6041
- promptTemplate: external_exports.string(),
6042
- model: external_exports.enum(["sonnet", "opus", "haiku"]).default("sonnet"),
6043
- lastRunAt: external_exports.coerce.date().optional(),
6044
- nextRunAt: external_exports.coerce.date().optional(),
6045
- enabled: external_exports.boolean().default(true),
6046
- retryCount: external_exports.number().int().nonnegative().default(0)
6047
- });
6048
- var RoutineRunSchema = external_exports.object({
6049
- id: external_exports.string().uuid(),
6050
- routineId: external_exports.string().uuid(),
6051
- startedAt: external_exports.coerce.date(),
6052
- completedAt: external_exports.coerce.date().optional(),
6053
- status: external_exports.enum(["success", "failed", "retried"]),
6054
- outputBriefId: external_exports.string().uuid().optional(),
6055
- errorMessage: external_exports.string().optional(),
6056
- inferenceCostCents: external_exports.number().int().nonnegative().default(0)
6057
- });
6058
- var BriefSchema = external_exports.object({
6059
- id: external_exports.string().uuid(),
6060
- studioId: external_exports.string().uuid(),
6061
- generatedAt: external_exports.coerce.date(),
6062
- type: external_exports.enum(["daily", "weekly", "on_demand"]),
6063
- html: external_exports.string().optional(),
6064
- markdown: external_exports.string(),
6065
- sourceLinks: external_exports.array(external_exports.object({ label: external_exports.string(), url: external_exports.string() })).default([]),
6066
- shared: external_exports.boolean().default(false),
6067
- shareToken: external_exports.string().optional(),
6068
- shareExpiresAt: external_exports.coerce.date().optional(),
6069
- inferenceCostCents: external_exports.number().int().nonnegative().default(0)
6070
- });
6071
- var MemoryEntrySchema = external_exports.object({
6072
- id: external_exports.string().uuid(),
6073
- productId: external_exports.string().uuid(),
6074
- kind: external_exports.enum(["decision", "fact", "customer", "status", "pattern", "thread"]),
6075
- content: external_exports.string(),
6076
- // embedding stored separately in pgvector; not modelled in API layer
6077
- createdAt: external_exports.coerce.date(),
6078
- lastReferencedAt: external_exports.coerce.date().optional(),
6079
- referenceCount: external_exports.number().int().nonnegative().default(0),
6080
- pinned: external_exports.boolean().default(false)
6081
- });
6082
- var InboxClassificationSchema = external_exports.object({
6083
- id: external_exports.string().uuid(),
6084
- emailAccountId: external_exports.string().uuid(),
6085
- productId: external_exports.string().uuid().nullable(),
6086
- messageId: external_exports.string(),
6087
- sender: external_exports.string(),
6088
- labelApplied: external_exports.string(),
6089
- urgency: external_exports.enum(["needs_reply", "fyi", "noise", "escalation"]),
6090
- confidence: external_exports.number().min(0).max(1),
6091
- action: external_exports.enum(["labelled", "archived", "drafted_reply"]),
6092
- userCorrected: external_exports.boolean().default(false),
6093
- correctedTo: external_exports.string().optional()
6094
- });
6095
- var DraftReplySchema = external_exports.object({
6096
- id: external_exports.string().uuid(),
6097
- classificationId: external_exports.string().uuid(),
6098
- draftText: external_exports.string(),
6099
- confidence: external_exports.number().min(0).max(1),
6100
- sentAt: external_exports.coerce.date().optional(),
6101
- sentVia: external_exports.string().optional()
6102
- });
6103
- var AlwaysAlertRuleSchema = external_exports.object({
6104
- id: external_exports.string().uuid(),
6105
- studioId: external_exports.string().uuid(),
6106
- ruleType: external_exports.enum(["sender", "subject", "domain"]),
6107
- value: external_exports.string(),
6108
- escalationMethod: external_exports.enum(["push", "slack", "email", "brief_pin"]).default("brief_pin")
6109
- });
6110
- var AuditEventSchema = external_exports.object({
6111
- id: external_exports.string().uuid(),
6112
- studioId: external_exports.string().uuid(),
6113
- actor: external_exports.enum(["user", "agent", "system"]),
6114
- action: external_exports.string(),
6115
- integrationId: external_exports.string().uuid().optional(),
6116
- productId: external_exports.string().uuid().optional(),
6117
- timestamp: external_exports.coerce.date(),
6118
- metadata: external_exports.record(external_exports.unknown()).default({})
6119
- });
6120
- var SubscriptionSchema = external_exports.object({
6121
- id: external_exports.string().uuid(),
6122
- studioId: external_exports.string().uuid(),
6123
- stripeSubscriptionId: external_exports.string().optional(),
6124
- tier: external_exports.enum(["trial", "solo", "studio", "studio_plus", "self_hosted", "enterprise"]),
6125
- seats: external_exports.number().int().positive(),
6126
- status: external_exports.string(),
6127
- currentPeriodEnd: external_exports.coerce.date(),
6128
- cancelAt: external_exports.coerce.date().optional()
6129
- });
6130
- var ProductMembershipSchema = external_exports.object({
6131
- humanId: external_exports.string().uuid(),
6132
- productId: external_exports.string().uuid(),
6133
- role: external_exports.enum(["lead", "contributor", "observer"])
6134
- });
6135
-
6136
- // ../witan/src/batch.ts
6137
- import { execFileSync as execFileSync3 } from "child_process";
6138
- import { mkdirSync as mkdirSync2, writeFileSync } from "fs";
6139
- import { basename as basename2, join as join5 } from "path";
6140
-
6141
- // ../witan/src/public-scan.ts
6142
- import { resolve as resolve2 } from "path";
6143
-
6144
- // ../witan/src/ingest.ts
6145
- import { readFileSync as readFileSync5, readdirSync as readdirSync2 } from "fs";
6146
- import { join as join2 } from "path";
4731
+ name: external_exports.string().min(1).max(300),
4732
+ digest: external_exports.object({
4733
+ sha256: external_exports.string().regex(/^[a-f0-9]{64}$/)
4734
+ }).strict()
4735
+ }).strict()
4736
+ ).length(1),
4737
+ predicateType: external_exports.literal(WITAN_ATTESTATION_PREDICATE_TYPE),
4738
+ predicate: external_exports.object({
4739
+ tool: external_exports.object({
4740
+ name: external_exports.literal("cejel"),
4741
+ version: external_exports.string().min(1).max(80)
4742
+ }).strict(),
4743
+ generatedAt: external_exports.string().datetime({ offset: true }),
4744
+ rubricVersion: external_exports.string().min(1).max(120),
4745
+ repository: external_exports.object({
4746
+ productSlug: external_exports.string().regex(/^[a-z0-9][a-z0-9-]{1,62}[a-z0-9]$/),
4747
+ url: external_exports.string().url().optional(),
4748
+ headSha: external_exports.string().min(7).max(64).optional()
4749
+ }).strict(),
4750
+ report: external_exports.object({
4751
+ artifact: external_exports.literal("report.json"),
4752
+ sha256: external_exports.string().regex(/^[a-f0-9]{64}$/)
4753
+ }).strict(),
4754
+ outcome: WitanAttestationOutcomeSchema,
4755
+ assurance: external_exports.object({
4756
+ status: external_exports.literal("unsigned"),
4757
+ issuer: external_exports.literal("self-generated"),
4758
+ signingHint: external_exports.string().min(1).max(500)
4759
+ }).strict(),
4760
+ limitations: external_exports.array(external_exports.string().min(1).max(500)).min(1).max(8)
4761
+ }).strict()
4762
+ }).strict();
6147
4763
 
6148
- // ../witan/src/finding-limits.ts
6149
- var RULE_ID_MAX = 200;
6150
- var MESSAGE_MAX = 500;
6151
- var LOCATION_MAX = 700;
6152
- function clamp(value, max) {
6153
- if (value.length <= max) return value;
6154
- const ellipsis = "...";
6155
- return `${value.slice(0, Math.max(max - ellipsis.length, 0))}${ellipsis}`;
6156
- }
6157
- function clampFinding(finding) {
6158
- return {
6159
- ...finding,
6160
- ruleId: clamp(finding.ruleId, RULE_ID_MAX),
6161
- message: clamp(finding.message, MESSAGE_MAX),
6162
- ...finding.location ? { location: clamp(finding.location, LOCATION_MAX) } : {}
4764
+ // src/witan/attestation.ts
4765
+ var ATTESTATION_LIMITATIONS = [
4766
+ "Cejel measures observable repository signals; it is not a security or compliance guarantee.",
4767
+ "This statement is self-generated and unsigned until an external signer binds their identity to it."
4768
+ ];
4769
+ function serializeWitanReport(report) {
4770
+ return JSON.stringify(report, null, 2);
4771
+ }
4772
+ function hashWitanReport(report) {
4773
+ return createHash("sha256").update(serializeWitanReport(report), "utf8").digest("hex");
4774
+ }
4775
+ function createWitanAttestation(report, options) {
4776
+ const reportSha256 = hashWitanReport(report);
4777
+ const outcome = report.insufficientSourceReason ? {
4778
+ status: "abstained",
4779
+ reason: report.insufficientSourceReason
4780
+ } : {
4781
+ status: "scored",
4782
+ overallScore: report.overallScore,
4783
+ codeTrustScore: report.codeTrustScore,
4784
+ processTrustScore: report.processTrustScore
6163
4785
  };
4786
+ return WitanAttestationStatementSchema.parse({
4787
+ _type: WITAN_ATTESTATION_STATEMENT_TYPE,
4788
+ subject: [
4789
+ {
4790
+ name: `${report.productSlug}/report.json`,
4791
+ digest: { sha256: reportSha256 }
4792
+ }
4793
+ ],
4794
+ predicateType: WITAN_ATTESTATION_PREDICATE_TYPE,
4795
+ predicate: {
4796
+ tool: { name: "cejel", version: options.toolVersion },
4797
+ generatedAt: report.generatedAt,
4798
+ rubricVersion: report.rubricVersion,
4799
+ repository: {
4800
+ productSlug: report.productSlug,
4801
+ ...report.repo.url ? { url: report.repo.url } : {},
4802
+ ...report.repo.headSha ? { headSha: report.repo.headSha } : {}
4803
+ },
4804
+ report: {
4805
+ artifact: "report.json",
4806
+ sha256: reportSha256
4807
+ },
4808
+ outcome,
4809
+ assurance: {
4810
+ status: "unsigned",
4811
+ issuer: "self-generated",
4812
+ signingHint: "Sign this in-toto statement with your existing provenance system; verify the report digest before relying on it."
4813
+ },
4814
+ limitations: [...ATTESTATION_LIMITATIONS]
4815
+ }
4816
+ });
6164
4817
  }
6165
4818
 
6166
- // ../witan/src/generic-adapter.ts
6167
- import { readFileSync as readFileSync2 } from "fs";
4819
+ // src/witan/repo-signals.ts
4820
+ import { execFileSync } from "child_process";
4821
+ import { createHash as createHash2 } from "crypto";
4822
+ import { readFileSync, readdirSync, realpathSync, statSync } from "fs";
4823
+ import { basename, join, relative, resolve, sep } from "path";
6168
4824
 
6169
- // ../witan/src/json-safe.ts
4825
+ // src/witan/json-safe.ts
6170
4826
  function stripBom(text) {
6171
4827
  return text.charCodeAt(0) === 65279 ? text.slice(1) : text;
6172
4828
  }
6173
4829
 
6174
- // ../witan/src/generic-adapter.ts
6175
- var VALID_DIMENSIONS = /* @__PURE__ */ new Set([
6176
- "A1",
6177
- "A2",
6178
- "A3",
6179
- "A4",
6180
- "A5",
6181
- "B1",
6182
- "B2",
6183
- "B3",
6184
- "B4",
6185
- "B5",
6186
- "B6"
6187
- ]);
6188
- var VALID_SEVERITIES = /* @__PURE__ */ new Set(["critical", "warning", "info"]);
6189
- function isGenericSignalDocument(raw) {
6190
- if (!raw || typeof raw !== "object" || Array.isArray(raw)) return false;
6191
- const doc = raw;
6192
- return typeof doc.tool === "string" && doc.tool.length > 0 && Array.isArray(doc.signals);
6193
- }
6194
- function parseGenericJson(raw) {
6195
- if (!isGenericSignalDocument(raw)) return [];
6196
- const source = raw.tool ?? "unknown";
6197
- const signals = [];
6198
- for (const signal of raw.signals ?? []) {
6199
- const dimension = signal.dimension;
6200
- if (!dimension || !VALID_DIMENSIONS.has(dimension)) continue;
6201
- const weight = typeof signal.weight === "number" && Number.isFinite(signal.weight) ? Math.min(Math.max(signal.weight, 0), 1) : 0.5;
6202
- const findings = [];
6203
- for (const finding of signal.findings ?? []) {
6204
- const severity = finding.severity;
6205
- if (!severity || !VALID_SEVERITIES.has(severity)) continue;
6206
- const ruleId = finding.ruleId ?? "unknown";
6207
- findings.push({
6208
- ruleId,
6209
- severity,
6210
- message: finding.message ?? ruleId,
6211
- ...finding.location ? { location: finding.location } : {}
6212
- });
6213
- }
6214
- if (findings.length === 0) continue;
6215
- signals.push({ source, dimension, weight, findings });
6216
- }
6217
- return signals;
6218
- }
6219
-
6220
- // ../witan/src/sarif-adapter.ts
6221
- import { readFileSync as readFileSync3 } from "fs";
6222
- var DIMENSION_RULES = [
6223
- // A2 — injection / secrets / auth (high weight)
6224
- {
6225
- pattern: /sql[- _]?inject|cwe-89|sqli|command[- _]?inject|cwe-78|os[- _]?cmd|rce|remote[- _]?code/i,
6226
- dimension: "A2",
6227
- weight: 0.9
6228
- },
6229
- {
6230
- pattern: /secret|credential|api[- _]?key|password[- _]?leak|hardcoded[- _]?(token|key|secret)|cwe-259|cwe-798/i,
6231
- dimension: "A2",
6232
- weight: 0.9
6233
- },
6234
- {
6235
- pattern: /path[- _]?traversal|directory[- _]?traversal|cwe-22|lfi|rfi/i,
6236
- dimension: "A2",
6237
- weight: 0.8
6238
- },
6239
- {
6240
- pattern: /ssrf|server[- _]?side[- _]?request[- _]?forg|cwe-918/i,
6241
- dimension: "A2",
6242
- weight: 0.8
6243
- },
6244
- {
6245
- pattern: /xxe|xml[- _]?external[- _]?entity|cwe-611/i,
6246
- dimension: "A2",
6247
- weight: 0.8
6248
- },
6249
- {
6250
- pattern: /auth[- _]?bypass|broken[- _]?auth|missing[- _]?auth|cwe-287|cwe-306|cwe-863|cwe-862/i,
6251
- dimension: "A2",
6252
- weight: 0.7
6253
- },
6254
- {
6255
- pattern: /xss|cross[- _]?site[- _]?script|cwe-79/i,
6256
- dimension: "A2",
6257
- weight: 0.6
6258
- },
6259
- // A4 — dependency vulnerabilities
6260
- {
6261
- pattern: /cve-\d{4}-\d+|supply[- _]?chain|depend[a-z]*[- _]?vulner|outdated[- _]?depend|deprecated[- _]?package/i,
6262
- dimension: "A4",
6263
- weight: 0.8
6264
- },
6265
- {
6266
- pattern: /npm[- _]?audit|yarn[- _]?audit|pnpm[- _]?audit|pip[- _]?audit|cargo[- _]?audit/i,
6267
- dimension: "A4",
6268
- weight: 0.7
6269
- },
6270
- // A3 — production readiness / insecure config
6271
- {
6272
- pattern: /insecure[- _]?tls|weak[- _]?cipher|tls[- _]?version|http[- _]?strict|hsts|csp[- _]?missing|cwe-326|cwe-327/i,
6273
- dimension: "A3",
6274
- weight: 0.5
6275
- },
6276
- {
6277
- pattern: /error[- _]?handl|unhandled[- _]?exception|crash|uncaught|stacktrace[- _]?leak/i,
6278
- dimension: "A3",
6279
- weight: 0.4
6280
- },
6281
- {
6282
- pattern: /debug[- _]?mode|dev[- _]?endpoint|staging[- _]?secret/i,
6283
- dimension: "A3",
6284
- weight: 0.4
6285
- },
6286
- // A1 — test integrity (low weight; SARIF rarely surfaces this)
6287
- {
6288
- pattern: /skipped[- _]?test|hollow[- _]?test|empty[- _]?assert|no[- _]?assertion/i,
6289
- dimension: "A1",
6290
- weight: 0.2
6291
- }
6292
- ];
6293
- var DEFAULT_DIMENSION = "A2";
6294
- var DEFAULT_WEIGHT = 0.3;
6295
- var DROP_LEVEL = /* @__PURE__ */ new Set(["none"]);
6296
- function mapLevel(level) {
6297
- if (!level || DROP_LEVEL.has(level)) return null;
6298
- if (level === "error") return "critical";
6299
- if (level === "warning") return "warning";
6300
- return "info";
6301
- }
6302
- function mapRuleToDimension(ruleId, rules) {
6303
- for (const rule of rules) {
6304
- if (rule.pattern.test(ruleId)) {
6305
- return { dimension: rule.dimension, weight: rule.weight };
6306
- }
6307
- }
6308
- return { dimension: DEFAULT_DIMENSION, weight: DEFAULT_WEIGHT };
6309
- }
6310
- function renderLocation(result) {
6311
- const loc = result.locations?.[0]?.physicalLocation;
6312
- if (!loc) return void 0;
6313
- const uri = loc.artifactLocation?.uri;
6314
- const line = loc.region?.startLine;
6315
- if (!uri) return void 0;
6316
- return line != null ? `${uri}:${line}` : uri;
6317
- }
6318
- function dedupeFindings(findings) {
6319
- const seen = /* @__PURE__ */ new Set();
6320
- return findings.filter((f) => {
6321
- const key = `${f.ruleId}|${f.severity}|${f.location ?? ""}`;
6322
- if (seen.has(key)) return false;
6323
- seen.add(key);
6324
- return true;
6325
- });
6326
- }
6327
- function parseSarifJson(raw, extraDimensionRules) {
6328
- if (!raw || typeof raw !== "object" || Array.isArray(raw)) return [];
6329
- const dimensionRules = extraDimensionRules ? [...DIMENSION_RULES, ...extraDimensionRules] : DIMENSION_RULES;
6330
- const doc = raw;
6331
- if (!Array.isArray(doc.runs)) return [];
6332
- const buckets = /* @__PURE__ */ new Map();
6333
- for (const run of doc.runs) {
6334
- const driverName = run.tool?.driver?.name ?? "unknown";
6335
- const source = `sarif:${driverName}`;
6336
- const ruleDefaultLevels = /* @__PURE__ */ new Map();
6337
- for (const rule of run.tool?.driver?.rules ?? []) {
6338
- if (rule.id && rule.defaultConfiguration?.level) {
6339
- ruleDefaultLevels.set(rule.id, rule.defaultConfiguration.level);
6340
- }
6341
- }
6342
- for (const result of run.results ?? []) {
6343
- const ruleId = result.ruleId ?? "unknown";
6344
- const effectiveLevel = result.level ?? ruleDefaultLevels.get(ruleId) ?? "warning";
6345
- const severity = mapLevel(effectiveLevel);
6346
- if (!severity) continue;
6347
- const message = result.message?.text ?? ruleId;
6348
- const location = renderLocation(result);
6349
- const { dimension, weight } = mapRuleToDimension(ruleId, dimensionRules);
6350
- const bucketKey = `${source}|${dimension}`;
6351
- if (!buckets.has(bucketKey)) {
6352
- buckets.set(bucketKey, { source, dimension, weight, findings: [] });
6353
- }
6354
- buckets.get(bucketKey)?.findings.push({ ruleId, severity, message, ...location ? { location } : {} });
6355
- }
6356
- }
6357
- return Array.from(buckets.values()).map(({ source, dimension, weight, findings }) => ({
6358
- source,
6359
- dimension,
6360
- weight,
6361
- findings: dedupeFindings(findings)
6362
- }));
6363
- }
6364
-
6365
- // ../witan/src/scorecard-adapter.ts
6366
- import { readFileSync as readFileSync4 } from "fs";
6367
- var CHECK_RULES = {
6368
- // B2 — PR outcome traceability
6369
- "Branch-Protection": { dimension: "B2", weight: 0.8 },
6370
- "Code-Review": { dimension: "B2", weight: 0.7 },
6371
- // B3 — CI and QA discipline
6372
- "Dangerous-Workflow": { dimension: "B3", weight: 0.9 },
6373
- "Token-Permissions": { dimension: "B3", weight: 0.8 },
6374
- "CI-Tests": { dimension: "B3", weight: 0.7 },
6375
- Maintained: { dimension: "B3", weight: 0.3 },
6376
- // B4 — audit trail / release integrity
6377
- "Signed-Releases": { dimension: "B4", weight: 0.7 },
6378
- Packaging: { dimension: "B4", weight: 0.4 },
6379
- "Security-Policy": { dimension: "B4", weight: 0.4 },
6380
- // A4 — dependency hygiene
6381
- Vulnerabilities: { dimension: "A4", weight: 0.9 },
6382
- "Pinned-Dependencies": { dimension: "A4", weight: 0.8 },
6383
- "Dependency-Update-Tool": { dimension: "A4", weight: 0.6 },
6384
- // A2 — data-layer / static analysis
6385
- SAST: { dimension: "A2", weight: 0.7 },
6386
- "Binary-Artifacts": { dimension: "A2", weight: 0.6 },
6387
- // A1 — test integrity
6388
- Fuzzing: { dimension: "A1", weight: 0.3 }
6389
- };
6390
- function mapScoreToSeverity(score) {
6391
- if (score == null || Number.isNaN(score)) return null;
6392
- if (score < 0) return null;
6393
- if (score >= 10) return null;
6394
- if (score <= 3) return "critical";
6395
- if (score <= 6) return "warning";
6396
- return "info";
6397
- }
6398
- function dedupeFindings2(findings) {
6399
- const seen = /* @__PURE__ */ new Set();
6400
- return findings.filter((f) => {
6401
- const key = `${f.ruleId}|${f.severity}|${f.location ?? ""}`;
6402
- if (seen.has(key)) return false;
6403
- seen.add(key);
6404
- return true;
6405
- });
6406
- }
6407
- function parseScorecardJson(raw) {
6408
- if (!raw || typeof raw !== "object" || Array.isArray(raw)) return [];
6409
- const doc = raw;
6410
- if (!Array.isArray(doc.checks)) return [];
6411
- const buckets = /* @__PURE__ */ new Map();
6412
- for (const check of doc.checks) {
6413
- const name = check.name;
6414
- if (!name) continue;
6415
- const rule = CHECK_RULES[name];
6416
- if (!rule) continue;
6417
- const severity = mapScoreToSeverity(check.score);
6418
- if (!severity) continue;
6419
- const scoreText = typeof check.score === "number" ? `${check.score}/10` : "n/a";
6420
- const message = `${name} (Scorecard ${scoreText}): ${check.reason ?? "weakness detected"}`.slice(0, 500);
6421
- const location = check.documentation?.url;
6422
- const bucket = buckets.get(rule.dimension) ?? { weight: 0, findings: [] };
6423
- bucket.weight = Math.max(bucket.weight, rule.weight);
6424
- bucket.findings.push({
6425
- ruleId: `scorecard:${name}`,
6426
- severity,
6427
- message,
6428
- ...location ? { location } : {}
6429
- });
6430
- buckets.set(rule.dimension, bucket);
6431
- }
6432
- return Array.from(buckets.entries()).map(([dimension, { weight, findings }]) => ({
6433
- source: "scorecard",
6434
- dimension,
6435
- weight,
6436
- findings: dedupeFindings2(findings)
6437
- }));
6438
- }
6439
-
6440
- // ../witan/src/ingest.ts
6441
- function looksLikeSarif(raw) {
6442
- if (!raw || typeof raw !== "object" || Array.isArray(raw)) return false;
6443
- return Array.isArray(raw.runs);
6444
- }
6445
- function looksLikeScorecard(raw) {
6446
- if (!raw || typeof raw !== "object" || Array.isArray(raw)) return false;
6447
- return Array.isArray(raw.checks);
6448
- }
6449
- function countRawEntries(raw) {
6450
- const obj = raw;
6451
- if (Array.isArray(obj.runs)) {
6452
- return obj.runs.reduce((sum, run) => {
6453
- const results = run.results;
6454
- return sum + (Array.isArray(results) ? results.length : 0);
6455
- }, 0);
6456
- }
6457
- if (Array.isArray(obj.checks)) return obj.checks.length;
6458
- if (Array.isArray(obj.signals)) {
6459
- return obj.signals.reduce((sum, signal) => {
6460
- const findings = signal.findings;
6461
- return sum + (Array.isArray(findings) ? findings.length : 0);
6462
- }, 0);
6463
- }
6464
- return 0;
6465
- }
6466
- function rawToolName(raw) {
6467
- const obj = raw;
6468
- if (Array.isArray(obj.runs)) {
6469
- const firstRun = obj.runs[0];
6470
- return firstRun?.tool?.driver?.name ?? "unknown";
6471
- }
6472
- if (typeof obj.tool === "string" && obj.tool.length > 0) return obj.tool;
6473
- return "scorecard";
6474
- }
6475
- function parseIngestFile(filePath) {
6476
- let raw;
6477
- try {
6478
- raw = JSON.parse(stripBom(readFileSync5(filePath, "utf8")));
6479
- } catch (error) {
6480
- const message = error instanceof Error ? error.message : String(error);
6481
- throw new Error(`Cejel: could not parse ingest file as JSON: ${filePath} (${message})`);
6482
- }
6483
- let signals;
6484
- if (looksLikeSarif(raw)) signals = parseSarifJson(raw);
6485
- else if (looksLikeScorecard(raw)) signals = parseScorecardJson(raw);
6486
- else if (isGenericSignalDocument(raw)) signals = parseGenericJson(raw);
6487
- if (!signals) {
6488
- throw new Error(
6489
- `Cejel: unrecognized ingest file format: ${filePath} \u2014 expected SARIF (a "runs" array), OpenSSF Scorecard JSON (a "checks" array), or the generic Cejel external-signal shape (a "tool" string + "signals" array). See the cejel README "Aggregate your scanners".`
6490
- );
6491
- }
6492
- const rawCount = countRawEntries(raw);
6493
- const mappedCount = signals.reduce((sum, signal) => sum + signal.findings.length, 0);
6494
- if (rawCount > 0 && mappedCount === 0) {
6495
- process.stderr.write(
6496
- `Cejel: ${rawCount} findings from ${rawToolName(raw)} (${filePath}), 0 mapped to trust criteria
6497
- `
6498
- );
6499
- }
6500
- return signals.map((signal) => ({
6501
- ...signal,
6502
- findings: signal.findings.map(clampFinding)
6503
- }));
6504
- }
6505
- function expandIngestPattern(pattern) {
6506
- if (!pattern.includes("*")) return [pattern];
6507
- const lastSlash = pattern.lastIndexOf("/");
6508
- const dir = lastSlash === -1 ? "." : pattern.slice(0, lastSlash);
6509
- const filePattern = lastSlash === -1 ? pattern : pattern.slice(lastSlash + 1);
6510
- const regexSource = filePattern.replace(/[.+^${}()|[\]\\]/g, "\\$&").replace(/\*/g, ".*");
6511
- const regex = new RegExp(`^${regexSource}$`);
6512
- let entries;
6513
- try {
6514
- entries = readdirSync2(dir);
6515
- } catch {
6516
- return [];
6517
- }
6518
- return entries.filter((name) => regex.test(name)).sort().map((name) => join2(dir, name));
6519
- }
6520
- function discoverIngestInputs(repoPath) {
6521
- const inputsDir = join2(repoPath, ".cejel", "inputs");
6522
- let entries;
6523
- try {
6524
- entries = readdirSync2(inputsDir);
6525
- } catch {
6526
- return [];
6527
- }
6528
- return entries.filter((name) => /\.(sarif|json)$/i.test(name)).sort().map((name) => join2(inputsDir, name));
6529
- }
6530
-
6531
- // ../witan/src/repo-signals.ts
6532
- import { execFileSync } from "child_process";
6533
- import { createHash } from "crypto";
6534
- import { readFileSync as readFileSync6, readdirSync as readdirSync3, realpathSync, statSync as statSync2 } from "fs";
6535
- import { basename, join as join3, relative, resolve, sep } from "path";
4830
+ // src/witan/repo-signals.ts
6536
4831
  function buildWitanInputFromRepo(options) {
6537
4832
  assertRepoPathExists(options.repoPath);
6538
4833
  const generatedAt = options.generatedAt ?? (/* @__PURE__ */ new Date()).toISOString();
@@ -6600,6 +4895,7 @@ var BUNDLED_BINARY_EXTENSION_PATTERN = /\.(vsix|zip|tgz|whl|exe|dmg|pkg|msi|jar|
6600
4895
  var DOCS_OR_MEDIA_EXTENSION_PATTERN = /\.(md|mdx|rst|png|jpe?g|gif|svg|webp|ico|pdf)$/i;
6601
4896
  var KNOWN_NON_SOURCE_EXTENSION_PATTERN = /\.(json|jsonc|json5|ya?ml|toml|txt|lock|xml|csv|tsv|ini|cfg|conf|properties|env|sum|mod|graphql|gql|proto|editorconfig|gitignore|gitattributes|npmrc|nvmrc|dockerignore|log|txt\.license)$/i;
6602
4897
  var INGEST_POINTER = "To assess a closed/bundled tool, ingest its scanner output via --ingest <sarif|scorecard>.";
4898
+ var SOURCE_DOMINANCE_RATIO_THRESHOLD = 0.2;
6603
4899
  function classifyRepoArchetype(repoFiles) {
6604
4900
  const totalFileCount = repoFiles.length;
6605
4901
  const sourceFileCount = repoFiles.filter((file) => SOURCE_EXTENSION_PATTERN.test(file)).length;
@@ -6611,57 +4907,83 @@ function classifyRepoArchetype(repoFiles) {
6611
4907
  insufficientSourceReason: "Repository has no tracked files \u2014 there is nothing to certify."
6612
4908
  };
6613
4909
  }
6614
- if (sourceFileCount > 0) {
4910
+ const unrecognisedSourceFiles = collectUnrecognisedSourceFiles(repoFiles);
4911
+ if (sourceFileCount === 0) {
4912
+ const binaryFiles = repoFiles.filter((file) => BUNDLED_BINARY_EXTENSION_PATTERN.test(file));
4913
+ if (binaryFiles.length > 0) {
4914
+ const sample = binaryFiles[0];
4915
+ return {
4916
+ archetype: "binary_only",
4917
+ sourceFileCount,
4918
+ totalFileCount,
4919
+ insufficientSourceReason: `${sourceFileCount} source file(s) found among ${totalFileCount} tracked file(s); repo appears to be a binary/bundled-distribution tree (e.g. ${sample ? basename(sample) : "a packaged artifact"}) \u2014 cejel rates source, not binaries. ${INGEST_POINTER}`
4920
+ };
4921
+ }
4922
+ const docsFiles = repoFiles.filter((file) => DOCS_OR_MEDIA_EXTENSION_PATTERN.test(file));
4923
+ if (docsFiles.length > 0 && docsFiles.length === totalFileCount) {
4924
+ return {
4925
+ archetype: "docs_only",
4926
+ sourceFileCount,
4927
+ totalFileCount,
4928
+ insufficientSourceReason: `${sourceFileCount} source file(s) found among ${totalFileCount} tracked file(s); repo appears to be a docs/distribution tree (README/markdown/media), not a source tree \u2014 cejel rates source, not docs. ${INGEST_POINTER}`
4929
+ };
4930
+ }
4931
+ if (unrecognisedSourceFiles.length > 0) {
4932
+ return unrecognisedEcosystemResult(sourceFileCount, totalFileCount, unrecognisedSourceFiles);
4933
+ }
4934
+ return { archetype: "source", sourceFileCount, totalFileCount };
4935
+ }
4936
+ if (unrecognisedSourceFiles.length === 0) {
6615
4937
  return {
6616
4938
  archetype: isLikelyMonorepo(repoFiles) ? "monorepo" : "source",
6617
4939
  sourceFileCount,
6618
4940
  totalFileCount
6619
4941
  };
6620
4942
  }
6621
- const binaryFiles = repoFiles.filter((file) => BUNDLED_BINARY_EXTENSION_PATTERN.test(file));
6622
- if (binaryFiles.length > 0) {
6623
- const sample = binaryFiles[0];
4943
+ const dominanceRatio = sourceFileCount / (sourceFileCount + unrecognisedSourceFiles.length);
4944
+ if (dominanceRatio >= SOURCE_DOMINANCE_RATIO_THRESHOLD) {
6624
4945
  return {
6625
- archetype: "binary_only",
6626
- sourceFileCount,
6627
- totalFileCount,
6628
- insufficientSourceReason: `${sourceFileCount} source file(s) found among ${totalFileCount} tracked file(s); repo appears to be a binary/bundled-distribution tree (e.g. ${sample ? basename(sample) : "a packaged artifact"}) \u2014 cejel rates source, not binaries. ${INGEST_POINTER}`
6629
- };
6630
- }
6631
- const docsFiles = repoFiles.filter((file) => DOCS_OR_MEDIA_EXTENSION_PATTERN.test(file));
6632
- if (docsFiles.length > 0 && docsFiles.length === totalFileCount) {
6633
- return {
6634
- archetype: "docs_only",
6635
- sourceFileCount,
6636
- totalFileCount,
6637
- insufficientSourceReason: `${sourceFileCount} source file(s) found among ${totalFileCount} tracked file(s); repo appears to be a docs/distribution tree (README/markdown/media), not a source tree \u2014 cejel rates source, not docs. ${INGEST_POINTER}`
6638
- };
6639
- }
6640
- const unrecognisedExtensions = collectUnrecognisedSourceExtensions(repoFiles);
6641
- if (unrecognisedExtensions.length > 0) {
6642
- const sample = unrecognisedExtensions.slice(0, 6).join(", ");
6643
- return {
6644
- archetype: "unrecognised_ecosystem",
4946
+ archetype: isLikelyMonorepo(repoFiles) ? "monorepo" : "source",
6645
4947
  sourceFileCount,
6646
- totalFileCount,
6647
- insufficientSourceReason: `Cejel does not yet read this repository's source language(s) (${sample}) \u2014 0 of ${totalFileCount} tracked file(s) matched a recognised source extension. Cejel abstains from a verdict rather than score a language it cannot parse; the Criterion Profile and Measured coverage below show exactly which dimensions were and were not measured. ${INGEST_POINTER}`
4948
+ totalFileCount
6648
4949
  };
6649
4950
  }
6650
- return { archetype: "source", sourceFileCount, totalFileCount };
4951
+ return unrecognisedEcosystemResult(sourceFileCount, totalFileCount, unrecognisedSourceFiles);
6651
4952
  }
6652
- function collectUnrecognisedSourceExtensions(repoFiles) {
6653
- const found = /* @__PURE__ */ new Set();
6654
- for (const file of repoFiles) {
4953
+ function collectUnrecognisedSourceFiles(repoFiles) {
4954
+ return repoFiles.filter((file) => {
6655
4955
  const base = basename(file);
6656
- const match = /\.([a-zA-Z0-9_]+)$/.exec(base);
4956
+ if (!/\.([a-zA-Z0-9_]+)$/.test(base)) return false;
4957
+ if (KNOWN_NON_SOURCE_EXTENSION_PATTERN.test(base)) return false;
4958
+ if (DOCS_OR_MEDIA_EXTENSION_PATTERN.test(base)) return false;
4959
+ if (BUNDLED_BINARY_EXTENSION_PATTERN.test(base)) return false;
4960
+ if (SOURCE_EXTENSION_PATTERN.test(base)) return false;
4961
+ return true;
4962
+ });
4963
+ }
4964
+ function extensionsByFileCountDescending(files) {
4965
+ const counts = /* @__PURE__ */ new Map();
4966
+ for (const file of files) {
4967
+ const match = /\.([a-zA-Z0-9_]+)$/.exec(basename(file));
6657
4968
  const ext = match?.[1];
6658
4969
  if (!ext) continue;
6659
- if (KNOWN_NON_SOURCE_EXTENSION_PATTERN.test(base)) continue;
6660
- if (DOCS_OR_MEDIA_EXTENSION_PATTERN.test(base)) continue;
6661
- if (BUNDLED_BINARY_EXTENSION_PATTERN.test(base)) continue;
6662
- found.add(`.${ext.toLowerCase()}`);
4970
+ const key = `.${ext.toLowerCase()}`;
4971
+ counts.set(key, (counts.get(key) ?? 0) + 1);
6663
4972
  }
6664
- return [...found].sort();
4973
+ return [...counts.entries()].sort(([extA, countA], [extB, countB]) => countB - countA || extA.localeCompare(extB)).map(([ext]) => ext);
4974
+ }
4975
+ function unrecognisedEcosystemResult(sourceFileCount, totalFileCount, unrecognisedSourceFiles) {
4976
+ const sample = extensionsByFileCountDescending(unrecognisedSourceFiles).slice(0, 6).join(", ");
4977
+ const candidateCount = sourceFileCount + unrecognisedSourceFiles.length;
4978
+ const dominancePct = candidateCount > 0 ? (sourceFileCount / candidateCount * 100).toFixed(1) : "0.0";
4979
+ const thresholdPct = (SOURCE_DOMINANCE_RATIO_THRESHOLD * 100).toFixed(0);
4980
+ const measuredClause = sourceFileCount > 0 ? `${sourceFileCount} of ${candidateCount} source-shaped file(s) (${dominancePct}%) are in a language Cejel reads \u2014 below the ${thresholdPct}% dominance threshold a score would need to be meaningful (${totalFileCount} tracked files in total; manifests, lockfiles, docs, media and bundled binaries are excluded from both sides of the ratio)` : `0 of ${totalFileCount} tracked file(s) matched a recognised source extension`;
4981
+ return {
4982
+ archetype: "unrecognised_ecosystem",
4983
+ sourceFileCount,
4984
+ totalFileCount,
4985
+ insufficientSourceReason: `Cejel does not yet read this repository's dominant source language(s) (${sample}) \u2014 ${measuredClause}. Cejel abstains from a verdict rather than score a repository whose recognised source is incidental rather than dominant; the Criterion Profile and Measured coverage below show exactly which dimensions were and were not measured. ${INGEST_POINTER}`
4986
+ };
6665
4987
  }
6666
4988
  function isLikelyMonorepo(repoFiles) {
6667
4989
  const packageRoots = new Set(
@@ -6672,7 +4994,7 @@ function isLikelyMonorepo(repoFiles) {
6672
4994
  function assertRepoPathExists(repoPath) {
6673
4995
  let stats;
6674
4996
  try {
6675
- stats = statSync2(repoPath);
4997
+ stats = statSync(repoPath);
6676
4998
  } catch {
6677
4999
  throw new Error(`Cejel: path not found: ${repoPath}`);
6678
5000
  }
@@ -6740,7 +5062,7 @@ function collectA1TestIntegrityEvidence(repoPath, repoFiles) {
6740
5062
  const runnerFiles = repoFiles.filter(isTestRunnerConfig).slice(0, 6);
6741
5063
  const coverageFiles = repoFiles.filter(isCoverageConfig).slice(0, 4);
6742
5064
  const packageJson = findRootPackageJson(repoFiles);
6743
- const packageScripts = packageJson ? readPackageScripts(join3(repoPath, packageJson)) : /* @__PURE__ */ new Map();
5065
+ const packageScripts = packageJson ? readPackageScripts(join(repoPath, packageJson)) : /* @__PURE__ */ new Map();
6744
5066
  const coveragePercent = readCoveragePercent(repoPath, coverageFiles);
6745
5067
  const ciWorkflows = repoFiles.filter(isCiWorkflow);
6746
5068
  const ciTestWorkflow = ciWorkflows.find(
@@ -7106,7 +5428,8 @@ function collectCryptoHygieneEvidence(repoPath, implFiles) {
7106
5428
  const findings = [];
7107
5429
  let hasSurface = false;
7108
5430
  let insecureFound = false;
7109
- const timingSafeFile = implFiles.find(
5431
+ const productionImplFiles = implFiles.filter(isProductionSourcePath);
5432
+ const timingSafeFile = productionImplFiles.find(
7110
5433
  (file) => fileContains(repoPath, file, TIMING_SAFE_COMPARE_PATTERN)
7111
5434
  );
7112
5435
  if (timingSafeFile) {
@@ -7120,7 +5443,7 @@ function collectCryptoHygieneEvidence(repoPath, implFiles) {
7120
5443
  )
7121
5444
  );
7122
5445
  }
7123
- const canonicalSignFile = implFiles.find(
5446
+ const canonicalSignFile = productionImplFiles.find(
7124
5447
  (file) => fileContains(repoPath, file, CANONICAL_SERIALIZE_PATTERN) && fileContains(repoPath, file, SIGN_OR_HMAC_CALL_PATTERN)
7125
5448
  );
7126
5449
  if (canonicalSignFile) {
@@ -7134,20 +5457,31 @@ function collectCryptoHygieneEvidence(repoPath, implFiles) {
7134
5457
  )
7135
5458
  );
7136
5459
  }
7137
- const insecureCompareFile = implFiles.find(
7138
- (file) => fileContains(repoPath, file, INSECURE_SECRET_COMPARE_PATTERN)
7139
- );
5460
+ let insecureCompareFile = null;
5461
+ let insecureCompareLine = null;
5462
+ for (const file of implFiles) {
5463
+ const line = findInsecureSecretCompareLine(repoPath, file);
5464
+ if (line != null) {
5465
+ insecureCompareFile = file;
5466
+ insecureCompareLine = line;
5467
+ break;
5468
+ }
5469
+ }
7140
5470
  if (insecureCompareFile) {
7141
- hasSurface = true;
7142
- insecureFound = true;
5471
+ const isTestPath = isTestOrFixturePath(insecureCompareFile);
5472
+ if (!isTestPath) {
5473
+ hasSurface = true;
5474
+ insecureFound = true;
5475
+ }
7143
5476
  findings.push({
7144
- severity: "warning",
7145
- summary: "A secret/HMAC/signature value appears compared with a plain equality operator instead of a constant-time comparison \u2014 potential timing side-channel.",
7146
- evidence: evidenceForRelative(
5477
+ severity: isTestPath ? "info" : "warning",
5478
+ summary: isTestPath ? `A secret/HMAC/signature comparison via plain equality appears in a test/fixture file (${insecureCompareFile}) \u2014 likely a test assertion, not a production timing leak; verify.` : "A secret/HMAC/signature value appears compared with a plain equality operator instead of a constant-time comparison \u2014 potential timing side-channel.",
5479
+ evidence: evidenceForRelativeAtLine(
7147
5480
  repoPath,
7148
5481
  insecureCompareFile,
7149
5482
  "artifact",
7150
- "Non-constant-time secret comparison"
5483
+ "Non-constant-time secret comparison",
5484
+ insecureCompareLine
7151
5485
  )
7152
5486
  });
7153
5487
  }
@@ -7155,16 +5489,25 @@ function collectCryptoHygieneEvidence(repoPath, implFiles) {
7155
5489
  (file) => fileContains(repoPath, file, UNSORTED_JSON_SIGN_PATTERN) && !fileContains(repoPath, file, CANONICAL_SERIALIZE_PATTERN)
7156
5490
  );
7157
5491
  if (unsortedSignFile) {
7158
- hasSurface = true;
7159
- insecureFound = true;
5492
+ const isTestPath = isTestOrFixturePath(unsortedSignFile);
5493
+ if (!isTestPath) {
5494
+ hasSurface = true;
5495
+ insecureFound = true;
5496
+ }
5497
+ const unsortedSignLine = findFirstMatchingLine(
5498
+ repoPath,
5499
+ unsortedSignFile,
5500
+ UNSORTED_JSON_SIGN_PATTERN
5501
+ );
7160
5502
  findings.push({
7161
- severity: "warning",
7162
- summary: "A signature/HMAC appears computed directly over JSON.stringify output with no canonical key ordering in the same file \u2014 signatures may not verify across equivalent payloads.",
7163
- evidence: evidenceForRelative(
5503
+ severity: isTestPath ? "info" : "warning",
5504
+ summary: isTestPath ? `Signing over unsorted JSON serialization appears in a test/fixture file (${unsortedSignFile}) \u2014 likely a test assertion, not a production signing gap; verify.` : "A signature/HMAC appears computed directly over JSON.stringify output with no canonical key ordering in the same file \u2014 signatures may not verify across equivalent payloads.",
5505
+ evidence: evidenceForRelativeAtLine(
7164
5506
  repoPath,
7165
5507
  unsortedSignFile,
7166
5508
  "artifact",
7167
- "Signing over unsorted JSON serialization"
5509
+ "Signing over unsorted JSON serialization",
5510
+ unsortedSignLine
7168
5511
  )
7169
5512
  });
7170
5513
  }
@@ -7180,7 +5523,7 @@ function collectA3ProdReadinessEvidence(repoPath, repoFiles) {
7180
5523
  const evidence = [];
7181
5524
  const findings = [];
7182
5525
  const packageJson = findRootPackageJson(repoFiles);
7183
- const scripts = packageJson ? readPackageScripts(join3(repoPath, packageJson)) : /* @__PURE__ */ new Map();
5526
+ const scripts = packageJson ? readPackageScripts(join(repoPath, packageJson)) : /* @__PURE__ */ new Map();
7184
5527
  const workflows = repoFiles.filter(isCiWorkflow);
7185
5528
  const workflow = workflows[0];
7186
5529
  const deployConfigs = repoFiles.filter(isDeployConfig);
@@ -7614,7 +5957,7 @@ function collectB2PrTraceEvidence(repoPath, repoFiles) {
7614
5957
  function collectB3CiDisciplineEvidence(repoPath, repoFiles, mono) {
7615
5958
  const evidence = [];
7616
5959
  const packageJson = findRootPackageJson(repoFiles);
7617
- const scripts = packageJson ? readPackageScripts(join3(repoPath, packageJson)) : /* @__PURE__ */ new Map();
5960
+ const scripts = packageJson ? readPackageScripts(join(repoPath, packageJson)) : /* @__PURE__ */ new Map();
7618
5961
  const workflows = repoFiles.filter(isCiWorkflow);
7619
5962
  const workflow = workflows[0];
7620
5963
  const rootWorkflows = mono ? mono.sharedFiles.filter(isCiWorkflow) : [];
@@ -7880,11 +6223,20 @@ function collectB6PrivilegedOpsGatingEvidence(repoPath, repoFiles) {
7880
6223
  var CPP_TEST_FRAMEWORK_PATTERN = /<gtest\/gtest\.h>|<catch2\/|<doctest\/|<boost\/test\/|"gtest\/gtest\.h"|"catch2\//;
7881
6224
  var CPP_TEST_MACRO_PATTERN = /\bTEST\s*\(|\bTEST_F\s*\(|\bTEST_CASE\s*\(|\bSECTION\s*\(|\bCATCH_|BOOST_AUTO_TEST_CASE\b|BOOST_FIXTURE_TEST_CASE\b/;
7882
6225
  var CPP_CONTENT_SCAN_LIMIT = 150;
7883
- var TEST_OR_FIXTURE_DIR_PATTERN = /(^|\/)(__tests__|__mocks__|__fixtures__|tests|test|fixtures|testdata|e2e|cypress)(\/|$)/i;
7884
- var TEST_OR_FIXTURE_FILE_PATTERN = /\.(test|spec|stories)\.[^/]+$/i;
6226
+ var NON_PRODUCTION_DIR_PATTERN = /(^|\/)(__tests__|__mocks__|__fixtures__|tests?|fixtures?|testdata|e2e|cypress|examples?|samples?|demos?)(\/|$)/i;
6227
+ var NON_PRODUCTION_FILE_SUFFIX_PATTERN = /\.(test|spec|stories)\.[^/]+$/i;
7885
6228
  function isTestOrFixturePath(path) {
7886
- return TEST_OR_FIXTURE_DIR_PATTERN.test(path) || TEST_OR_FIXTURE_FILE_PATTERN.test(path);
6229
+ return NON_PRODUCTION_DIR_PATTERN.test(path) || NON_PRODUCTION_FILE_SUFFIX_PATTERN.test(path);
6230
+ }
6231
+ function isProductionSourcePath(path) {
6232
+ return !isTestOrFixturePath(path);
7887
6233
  }
6234
+ function isTestFile(file) {
6235
+ return /(^|\/)(__tests__|test|tests|spec)\/.*\.(?:[cm]?[jt]sx?|py|go|rs|java|rb|cpp|cc|cxx)$/.test(
6236
+ file
6237
+ ) || /\.(test|spec)\.[cm]?[jt]sx?$/.test(file) || /(^|\/)test_.*\.py$/.test(file) || /_test\.go$/.test(file) || /(^|\/)test_.*\.(cpp|cc|cxx)$/.test(file) || /_(test|tests)\.(cpp|cc|cxx)$/.test(file) || /Tests?\.(java|kt)$/.test(file) || /(_test|_spec)\.(rs|rb|php|swift|kt)$/.test(file);
6238
+ }
6239
+ var NAME_SHAPED_TEST_FILE_PATTERN = /\.(test|spec)\.[cm]?[jt]sx?$|(^|\/)__tests__\/|(^|\/)test_[^/]*\.py$|(^|\/)tests?\.py$|_test\.go$|(^|\/)test_[^/]*\.(cpp|cc|cxx)$|_(test|tests)\.(cpp|cc|cxx)$|Tests?\.(java|kt)$|(_test|_spec)\.(rs|rb|php|swift|kt)$/;
7888
6240
  var TEST_RUNNER_PATTERN = /\b(vitest|jest|mocha|ava|tap|pytest|go test|cargo test|rspec|phpunit|gradle test|mvn test)\b/i;
7889
6241
  var CI_TEST_COMMAND_PATTERN = /\b(pytest|go\s+test|cargo\s+test|mvn\s+test|gradle\s+test|ctest|make\s+test|jest|vitest|mocha|rspec|phpunit|pnpm\s+test|npm\s+test|yarn\s+test|node\s+--test|node:test)\b/i;
7890
6242
  var CI_LINT_COMMAND_PATTERN = /\b(eslint|pylint|flake8|black|ruff)\b/i;
@@ -7917,7 +6269,28 @@ var HEAVY_TEST_DEPENDENCY_NAME_PATTERN = /^(?:jest|mocha|ava|tape|jasmine|karma)
7917
6269
  var TIMING_SAFE_COMPARE_PATTERN = /\btiming[-_]?safe[-_]?(?:equal|compare)\b|crypto\.timingSafeEqual\s*\(/i;
7918
6270
  var CANONICAL_SERIALIZE_PATTERN = /\bcanonicalize\s*\(|\bcanonicalJson\b|\bstableStringify\s*\(|json-stable-stringify|safe-stable-stringify|\bsortKeys\s*\(/i;
7919
6271
  var SIGN_OR_HMAC_CALL_PATTERN = /\bcreateHmac\s*\(|\bcreateSign\s*\(|\.sign\s*\(/;
7920
- var INSECURE_SECRET_COMPARE_PATTERN = /\b\w*(?:hmac|signature|\bmac|digest)\w*\s*(?:===|!==)\s*(?!['"`]|undefined\b|null\b)\w/i;
6272
+ var INSECURE_SECRET_COMPARE_LINE_PATTERN = /\b\w*(?:hmac|signature|\bmac|digest)\w*\s*(===|!==)\s*(?!['"`]|undefined\b|null\b)([\w.]+(?:\s*[-+]\s*\d+)?)/i;
6273
+ var NUMERIC_SHAPED_OPERAND_PATTERN = /^-?\d+$|\.(?:length|len|size|count)\b|(?:length|index|idx|offset|count|size|len)$/i;
6274
+ function lineHasInsecureSecretCompare(line) {
6275
+ const match = INSECURE_SECRET_COMPARE_LINE_PATTERN.exec(line);
6276
+ const operand = match?.[2];
6277
+ if (!operand) return false;
6278
+ return !NUMERIC_SHAPED_OPERAND_PATTERN.test(operand.trim());
6279
+ }
6280
+ function findInsecureSecretCompareLine(repoPath, file) {
6281
+ const fullPath = join(repoPath, file);
6282
+ if (!isRegularFile(fullPath)) return null;
6283
+ const lines = readFileSync(fullPath, "utf8").split("\n");
6284
+ const index = lines.findIndex((line) => lineHasInsecureSecretCompare(line));
6285
+ return index === -1 ? null : index + 1;
6286
+ }
6287
+ function findFirstMatchingLine(repoPath, file, pattern) {
6288
+ const fullPath = join(repoPath, file);
6289
+ if (!isRegularFile(fullPath)) return null;
6290
+ const lines = readFileSync(fullPath, "utf8").split("\n");
6291
+ const index = lines.findIndex((line) => pattern.test(line));
6292
+ return index === -1 ? null : index + 1;
6293
+ }
7921
6294
  var UNSORTED_JSON_SIGN_PATTERN = /\.update\s*\(\s*JSON\.stringify\s*\(|\.sign\s*\([^)]*JSON\.stringify\s*\(/;
7922
6295
  var KILL_SWITCH_NAME_FRAGMENT = "kill[_-]?switch|emergency[_-]?stop|circuit[_-]?breaker|safety[_-]?(?:toggle|gate|switch)|governance[_-]?(?:toggle|gate)";
7923
6296
  var KILL_SWITCH_NAME_PATTERN = new RegExp(`\\b(?:${KILL_SWITCH_NAME_FRAGMENT})\\b`, "i");
@@ -8029,13 +6402,13 @@ function listGitTrackedFiles(repoPath) {
8029
6402
  function visitRepoDir(repoPath, dirPath, files) {
8030
6403
  let entries;
8031
6404
  try {
8032
- entries = readdirSync3(dirPath, { withFileTypes: true });
6405
+ entries = readdirSync(dirPath, { withFileTypes: true });
8033
6406
  } catch {
8034
6407
  return;
8035
6408
  }
8036
6409
  for (const entry of entries) {
8037
6410
  if (shouldSkipDir(entry.name)) continue;
8038
- const fullPath = join3(dirPath, entry.name);
6411
+ const fullPath = join(dirPath, entry.name);
8039
6412
  if (entry.isDirectory()) {
8040
6413
  visitRepoDir(repoPath, fullPath, files);
8041
6414
  continue;
@@ -8043,7 +6416,7 @@ function visitRepoDir(repoPath, dirPath, files) {
8043
6416
  if (!entry.isFile()) continue;
8044
6417
  let size;
8045
6418
  try {
8046
- size = statSync2(fullPath).size;
6419
+ size = statSync(fullPath).size;
8047
6420
  } catch {
8048
6421
  continue;
8049
6422
  }
@@ -8068,20 +6441,15 @@ function shouldSkipDir(name) {
8068
6441
  "target"
8069
6442
  ].includes(name);
8070
6443
  }
8071
- function isHardExcludedPath(path) {
8072
- return HARD_EXCLUDED_PATH_PATTERN.test(path);
8073
- }
8074
- function isTestFile(file) {
8075
- return /(^|\/)(__tests__|test|tests|spec)\/.*\.(?:[cm]?[jt]sx?|py|go|rs|java|rb|cpp|cc|cxx)$/.test(
8076
- file
8077
- ) || /\.(test|spec)\.[cm]?[jt]sx?$/.test(file) || /(^|\/)test_.*\.py$/.test(file) || /_test\.go$/.test(file) || /(^|\/)test_.*\.(cpp|cc|cxx)$/.test(file) || /_(test|tests)\.(cpp|cc|cxx)$/.test(file) || /Tests?\.(java|kt)$/.test(file) || /(_test|_spec)\.(rs|rb|php|swift|kt)$/.test(file);
8078
- }
6444
+ function isHardExcludedPath(path) {
6445
+ return HARD_EXCLUDED_PATH_PATTERN.test(path);
6446
+ }
8079
6447
  function collectContentBasedCppTestFiles(repoPath, repoFiles) {
8080
6448
  const candidates = repoFiles.filter((file) => /\.(cpp|cc|cxx)$/.test(file) && !isTestFile(file)).slice(0, CPP_CONTENT_SCAN_LIMIT);
8081
6449
  return candidates.filter((file) => {
8082
- const fullPath = join3(repoPath, file);
6450
+ const fullPath = join(repoPath, file);
8083
6451
  if (!isRegularFile(fullPath)) return false;
8084
- const contents = readFileSync6(fullPath, "utf8");
6452
+ const contents = readFileSync(fullPath, "utf8");
8085
6453
  return CPP_TEST_FRAMEWORK_PATTERN.test(contents) || CPP_TEST_MACRO_PATTERN.test(contents);
8086
6454
  });
8087
6455
  }
@@ -8095,14 +6463,13 @@ var JS_TEST_ASSERTION_PATTERN = /(expect\(|assert\.|should\.|toEqual\(|toBe\(|as
8095
6463
  var CPP_TEST_ASSERTION_PATTERN = /\bEXPECT_|ASSERT_EQ\b|ASSERT_TRUE\b|ASSERT_FALSE\b|\bREQUIRE\s*\(|\bCHECK\s*\(|\bTEST\s*\(|\bTEST_F\s*\(|\bTEST_CASE\s*\(|\bSECTION\s*\(/;
8096
6464
  var MULTI_ECOSYSTEM_TEST_ASSERTION_PATTERN = /\.assert[A-Z_]\w*\s*\(|\bassert[A-Z]\w*\s*\(|\bpytest\.raises\b|\bself\.fail\s*\(|\bt\.(?:Error|Errorf|Fatal|Fatalf|Fail|FailNow)\b|\brequire\.[A-Z]\w*\s*\(|\b(?:debug_)?assert(?:_eq|_ne)?!\s*\(|\bassert_\w+\b|\$this->assert\w+\s*\(/;
8097
6465
  var SUITE_LEVEL_SKIP_PATTERN = /\b(?:describe|suite|context)\.skip\s*\(/;
8098
- var NAME_SHAPED_TEST_FILE_PATTERN = /\.(test|spec)\.[cm]?[jt]sx?$|(^|\/)__tests__\/|(^|\/)test_[^/]*\.py$|(^|\/)tests?\.py$|_test\.go$|(^|\/)test_[^/]*\.(cpp|cc|cxx)$|_(test|tests)\.(cpp|cc|cxx)$|Tests?\.(java|kt)$|(_test|_spec)\.(rs|rb|php|swift|kt)$/;
8099
6466
  function measureNonHollowTestShare(repoPath, files) {
8100
6467
  let nonHollowCount = 0;
8101
6468
  let ratedCount = 0;
8102
6469
  for (const file of files) {
8103
- const fullPath = join3(repoPath, file);
6470
+ const fullPath = join(repoPath, file);
8104
6471
  if (!isRegularFile(fullPath)) continue;
8105
- const contents = readFileSync6(fullPath, "utf8");
6472
+ const contents = readFileSync(fullPath, "utf8");
8106
6473
  const nonHollow = (JS_TEST_ASSERTION_PATTERN.test(contents) || CPP_TEST_ASSERTION_PATTERN.test(contents) || MULTI_ECOSYSTEM_TEST_ASSERTION_PATTERN.test(contents)) && !SUITE_LEVEL_SKIP_PATTERN.test(contents);
8107
6474
  if (nonHollow) {
8108
6475
  nonHollowCount += 1;
@@ -8121,17 +6488,17 @@ function countPatternMatches(repoPath, files, pattern) {
8121
6488
  const matcher = new RegExp(pattern.source, flags);
8122
6489
  let count = 0;
8123
6490
  for (const file of files) {
8124
- const fullPath = join3(repoPath, file);
6491
+ const fullPath = join(repoPath, file);
8125
6492
  if (!isRegularFile(fullPath)) continue;
8126
- count += [...readFileSync6(fullPath, "utf8").matchAll(matcher)].length;
6493
+ count += [...readFileSync(fullPath, "utf8").matchAll(matcher)].length;
8127
6494
  }
8128
6495
  return count;
8129
6496
  }
8130
6497
  function readCoveragePercent(repoPath, files) {
8131
6498
  for (const file of files) {
8132
- const fullPath = join3(repoPath, file);
6499
+ const fullPath = join(repoPath, file);
8133
6500
  if (!isRegularFile(fullPath)) continue;
8134
- const contents = readFileSync6(fullPath, "utf8");
6501
+ const contents = readFileSync(fullPath, "utf8");
8135
6502
  const summaryPercent = parseCoverageSummaryPercent(contents);
8136
6503
  if (summaryPercent !== null) return summaryPercent;
8137
6504
  const thresholdPercent = parseCoverageThresholdPercent(contents);
@@ -8175,7 +6542,7 @@ function pickPrimaryDependencyManifest(repoPath, manifests) {
8175
6542
  function readDependencySpecs(repoPath, manifests) {
8176
6543
  const specs = [];
8177
6544
  for (const manifest of manifests) {
8178
- const fullPath = join3(repoPath, manifest);
6545
+ const fullPath = join(repoPath, manifest);
8179
6546
  if (!isRegularFile(fullPath)) continue;
8180
6547
  if (manifest.endsWith("package.json")) {
8181
6548
  specs.push(...readPackageJsonDependencySpecs(fullPath));
@@ -8221,7 +6588,7 @@ function readDependencySpecs(repoPath, manifests) {
8221
6588
  }
8222
6589
  function readGoModDependencySpecs(path) {
8223
6590
  const specs = [];
8224
- const contents = readFileSync6(path, "utf8");
6591
+ const contents = readFileSync(path, "utf8");
8225
6592
  const blockPattern = /require\s*\(([^)]+)\)/gs;
8226
6593
  const singlePattern = /^require\s+(\S+)\s+(\S+)/gm;
8227
6594
  for (const blockMatch of contents.matchAll(blockPattern)) {
@@ -8242,7 +6609,7 @@ function readGoModDependencySpecs(path) {
8242
6609
  }
8243
6610
  function readCargoTomlDependencySpecs(path) {
8244
6611
  const specs = [];
8245
- const contents = readFileSync6(path, "utf8");
6612
+ const contents = readFileSync(path, "utf8");
8246
6613
  const depSectionPattern = /^\[(?:dependencies|dev-dependencies|build-dependencies)\]([\s\S]*?)(?=^\[|(?![\s\S]))/gm;
8247
6614
  for (const sectionMatch of contents.matchAll(depSectionPattern)) {
8248
6615
  const section = sectionMatch[1] ?? "";
@@ -8264,7 +6631,7 @@ function readCargoTomlDependencySpecs(path) {
8264
6631
  }
8265
6632
  function readPyprojectDependencySpecs(path) {
8266
6633
  const specs = [];
8267
- const contents = readFileSync6(path, "utf8");
6634
+ const contents = readFileSync(path, "utf8");
8268
6635
  const poetrySectionPattern = /^\[tool\.poetry\.dependencies\]([\s\S]*?)(?=^\[|(?![\s\S]))/gm;
8269
6636
  for (const sectionMatch of contents.matchAll(poetrySectionPattern)) {
8270
6637
  const section = sectionMatch[1] ?? "";
@@ -8298,7 +6665,7 @@ function readPyprojectDependencySpecs(path) {
8298
6665
  }
8299
6666
  function readPipfileDependencySpecs(path) {
8300
6667
  const specs = [];
8301
- const contents = readFileSync6(path, "utf8");
6668
+ const contents = readFileSync(path, "utf8");
8302
6669
  const sectionPattern = /^\[(?:packages|dev-packages)\]([\s\S]*?)(?=^\[|$(?![\s\S]))/gm;
8303
6670
  for (const sectionMatch of contents.matchAll(sectionPattern)) {
8304
6671
  for (const line of (sectionMatch[1] ?? "").split("\n")) {
@@ -8311,7 +6678,7 @@ function readPipfileDependencySpecs(path) {
8311
6678
  return specs;
8312
6679
  }
8313
6680
  function readVcpkgJsonDependencySpecs(path) {
8314
- const parsed = parseJsonObject(readFileSync6(path, "utf8"));
6681
+ const parsed = parseJsonObject(readFileSync(path, "utf8"));
8315
6682
  if (!parsed) return [];
8316
6683
  const rawDeps = Array.isArray(parsed.dependencies) ? parsed.dependencies : [];
8317
6684
  const specs = [];
@@ -8327,7 +6694,7 @@ function readVcpkgJsonDependencySpecs(path) {
8327
6694
  }
8328
6695
  function readConanfileTxtDependencySpecs(path) {
8329
6696
  const specs = [];
8330
- const contents = readFileSync6(path, "utf8");
6697
+ const contents = readFileSync(path, "utf8");
8331
6698
  const requiresMatch = /^\[requires\]([\s\S]*?)(?=^\[|$(?![\s\S]))/m.exec(contents);
8332
6699
  if (!requiresMatch) return specs;
8333
6700
  for (const line of (requiresMatch[1] ?? "").split("\n")) {
@@ -8340,7 +6707,7 @@ function readConanfileTxtDependencySpecs(path) {
8340
6707
  }
8341
6708
  function readConanfilePyDependencySpecs(path) {
8342
6709
  const specs = [];
8343
- const contents = readFileSync6(path, "utf8");
6710
+ const contents = readFileSync(path, "utf8");
8344
6711
  for (const match of contents.matchAll(/self\.requires\s*\(\s*["']([\w.\-]+)\/([\w.\-]+)["']/g)) {
8345
6712
  specs.push({ name: match[1] ?? "", version: match[2] ?? "" });
8346
6713
  }
@@ -8354,7 +6721,7 @@ function readConanfilePyDependencySpecs(path) {
8354
6721
  }
8355
6722
  function readCMakeDependencySpecs(path) {
8356
6723
  const specs = [];
8357
- const contents = readFileSync6(path, "utf8");
6724
+ const contents = readFileSync(path, "utf8");
8358
6725
  for (const match of contents.matchAll(/find_package\s*\(\s*([\w]+)(?:\s+([\d.]+))?/gi)) {
8359
6726
  const name = match[1];
8360
6727
  if (!name) continue;
@@ -8369,7 +6736,7 @@ function readCMakeDependencySpecs(path) {
8369
6736
  return specs;
8370
6737
  }
8371
6738
  function readPackageJsonDependencySpecs(packageJsonPath) {
8372
- const parsed = parseJsonObject(readFileSync6(packageJsonPath, "utf8"));
6739
+ const parsed = parseJsonObject(readFileSync(packageJsonPath, "utf8"));
8373
6740
  if (!parsed) return [];
8374
6741
  const optionalPeerNames = /* @__PURE__ */ new Set();
8375
6742
  const peerDependenciesMeta = parsed.peerDependenciesMeta;
@@ -8396,7 +6763,7 @@ function readPackageJsonDependencySpecs(packageJsonPath) {
8396
6763
  return specs;
8397
6764
  }
8398
6765
  function readRequirementsDependencySpecs(path) {
8399
- return readFileSync6(path, "utf8").split("\n").map((line) => line.trim()).filter((line) => line.length > 0 && !line.startsWith("#")).map((line) => {
6766
+ return readFileSync(path, "utf8").split("\n").map((line) => line.trim()).filter((line) => line.length > 0 && !line.startsWith("#")).map((line) => {
8400
6767
  const [name = line, version = ""] = line.split(/[<>=~!]=?/, 2);
8401
6768
  return { name: name.trim(), version: line.includes("==") ? version.trim() : line };
8402
6769
  });
@@ -8412,9 +6779,9 @@ function isPinnedDependencyVersion(version) {
8412
6779
  return /^\d+\.\d+(?:\.\d+)?(?:[-+][0-9A-Za-z.-]+)?$/.test(trimmed);
8413
6780
  }
8414
6781
  function workflowTargetsDefaultBranch(repoPath, file) {
8415
- const fullPath = join3(repoPath, file);
6782
+ const fullPath = join(repoPath, file);
8416
6783
  if (!isRegularFile(fullPath)) return false;
8417
- const contents = readFileSync6(fullPath, "utf8").toLowerCase();
6784
+ const contents = readFileSync(fullPath, "utf8").toLowerCase();
8418
6785
  return /\bpull_request\b/.test(contents) || /\bbranches:\s*\[[^\]]*\b(main|master)\b[^\]]*\]/.test(contents) || /\bbranches:\s*\n\s*-\s*(main|master)\b/.test(contents);
8419
6786
  }
8420
6787
  function isPrMergeCommit(commit) {
@@ -8450,7 +6817,6 @@ function isExplicitDeployTarget(file) {
8450
6817
  return /^(vercel|netlify|fly|render|railway)\.(json|toml|ya?ml)$/.test(file) || /^docker-compose\.ya?ml$/.test(file) || /^Procfile$/.test(file) || /^app\.ya?ml$/.test(file) || /^serverless\.ya?ml$/.test(file) || /^(k8s|kubernetes|manifests?)\/.+\.ya?ml$/i.test(file) || /^(charts?|helm)\/.+\.ya?ml$/i.test(file);
8451
6818
  }
8452
6819
  var MAIN_ENTRYPOINT_FILE_PATTERN = /(^|\/)(main|server|app|wsgi|asgi|index|entry|start|run)\.(ts|tsx|js|jsx|mjs|cjs|py|go|rs)$/i;
8453
- var EXAMPLE_OR_TEST_DIR_PATTERN = /(?:^|\/)(examples?|samples?|demos?|tests?|__tests__|spec|fixtures?)(?:\/|$)/i;
8454
6820
  var SERVER_ENTRYPOINT_PATTERN = /\bapp\.listen\s*\(|\bserver\.listen\s*\(\s*(?:PORT|port|\d+)|http\.ListenAndServe\s*\(|http\.ListenAndServeTLS\s*\(|axum::Server(?:::|\.)|actix_web::HttpServer(?:::|\.)|uvicorn\.run\s*\(/;
8455
6821
  var CI_DEPLOY_JOB_PATTERN = /(?:^\s{2,4}deploy\s*:|\b(?:fly|heroku|vercel|netlify|railway|render)\s+deploy\b|kubectl\s+apply\b|helm\s+(?:install|upgrade|deploy)\b|docker\s+push\b)/im;
8456
6822
  function isDeployableService(repoPath, repoFiles) {
@@ -8467,9 +6833,7 @@ function detectServerEntrypoint(repoPath, repoFiles) {
8467
6833
  return findServerEntrypointFile(repoPath, repoFiles) !== null;
8468
6834
  }
8469
6835
  function findServerEntrypointFile(repoPath, repoFiles) {
8470
- const candidates = repoFiles.filter(
8471
- (file) => MAIN_ENTRYPOINT_FILE_PATTERN.test(file) && !EXAMPLE_OR_TEST_DIR_PATTERN.test(file)
8472
- ).slice(0, 30);
6836
+ const candidates = repoFiles.filter((file) => MAIN_ENTRYPOINT_FILE_PATTERN.test(file) && isProductionSourcePath(file)).slice(0, 30);
8473
6837
  return candidates.find((file) => fileContains(repoPath, file, SERVER_ENTRYPOINT_PATTERN)) ?? null;
8474
6838
  }
8475
6839
  function isHealthCheckSignalFile(repoPath, file) {
@@ -8481,391 +6845,785 @@ function isHealthCheckSignalFile(repoPath, file) {
8481
6845
  if (/(^|\/)(health|healthcheck|readiness|liveness|ready)\.[cm]?[jt]sx?$/.test(file)) {
8482
6846
  return fileContains(repoPath, file, /health|ready|readiness|liveness/i);
8483
6847
  }
8484
- if (/(^|\/)(health|healthcheck|readiness|liveness|ready)\.py$/.test(file)) {
8485
- return fileContains(repoPath, file, /health|ready|readiness|liveness/i);
6848
+ if (/(^|\/)(health|healthcheck|readiness|liveness|ready)\.py$/.test(file)) {
6849
+ return fileContains(repoPath, file, /health|ready|readiness|liveness/i);
6850
+ }
6851
+ return false;
6852
+ }
6853
+ function isDependencyManifest(file) {
6854
+ return /(^|\/)(package\.json|pyproject\.toml|requirements(?:[^/]*)?\.txt|go\.mod|Cargo\.toml|pom\.xml|build\.gradle|vcpkg\.json|Pipfile|CMakeLists\.txt|conanfile\.txt|conanfile\.py)$/.test(
6855
+ file
6856
+ );
6857
+ }
6858
+ function isLockfile(file) {
6859
+ return /(^|\/)(pnpm-lock\.yaml|package-lock\.json|yarn\.lock|uv\.lock|poetry\.lock|go\.sum|Cargo\.lock|Pipfile\.lock|composer\.lock|conan\.lock|vcpkg\.lock\.json)$/.test(
6860
+ file
6861
+ );
6862
+ }
6863
+ function isDependencyUpdateConfig(file) {
6864
+ return /(^|\/)(renovate\.json|renovate\.json5|\.renovaterc\.json|dependabot\.ya?ml)$/.test(file) || /^\.github\/dependabot\.ya?ml$/.test(file);
6865
+ }
6866
+ function packageJsonHasAuditScript(repoPath, manifest) {
6867
+ if (!manifest.endsWith("package.json")) return false;
6868
+ const scripts = readPackageScripts(join(repoPath, manifest));
6869
+ return [...scripts.values()].some(
6870
+ (script) => /\b(audit|npm audit|pnpm audit|yarn audit)\b/i.test(script)
6871
+ );
6872
+ }
6873
+ function packageJsonHasHeavyTestDependency(repoPath, manifest) {
6874
+ const fullPath = join(repoPath, manifest);
6875
+ if (!isRegularFile(fullPath)) return false;
6876
+ const parsed = parseJsonObject(readFileSync(fullPath, "utf8"));
6877
+ if (!parsed) return false;
6878
+ const names = [
6879
+ ...Object.keys(isRecord(parsed.dependencies) ? parsed.dependencies : {}),
6880
+ ...Object.keys(isRecord(parsed.devDependencies) ? parsed.devDependencies : {})
6881
+ ];
6882
+ return names.some((name) => HEAVY_TEST_DEPENDENCY_NAME_PATTERN.test(name));
6883
+ }
6884
+ function isImplementationFile(file) {
6885
+ return /(^|\/)(src|app|lib|packages|cmd|include|source|Sources)\//.test(file) && /\.(ts|tsx|js|jsx|py|go|rs|java|rb|cpp|cc|cxx|c|h|hpp|kt|swift|php)$/.test(file);
6886
+ }
6887
+ function isAuditFile(file) {
6888
+ return (
6889
+ // goal_cejel_calibration_fix_with_strict_gate_2026-07-06: mature OSS repos document the
6890
+ // same audit-trail practice under different filenames/extensions than Alfred's own
6891
+ // conventions (Flask ships CHANGES.rst, not CHANGELOG.md) — recognize the common OSS
6892
+ // release-notes/security-policy/provenance equivalents so real audit-trail artifacts are
6893
+ // credited instead of silently missing the pattern.
6894
+ /(^|\/)(CHANGELOG|CHANGES|HISTORY|NEWS|RELEASE_NOTES|RELEASES|SECURITY|AUDIT|STATUS)\.(md|rst|txt)$/i.test(
6895
+ file
6896
+ ) || /(^|\/)docs\/.*(audit|runbook|incident|changelog|security).*\.(md|rst)$/i.test(file) || // Provenance/signed-release tooling config is itself audit-trail evidence (a repo that
6897
+ // wires SLSA/cosign attestation or CITATION.cff is documenting release provenance).
6898
+ /(^|\/)CITATION\.cff$/i.test(file)
6899
+ );
6900
+ }
6901
+ function isSecurityPolicyOnlyAuditFile(file) {
6902
+ return /(^|\/)SECURITY\.(md|rst|txt)$/i.test(file) || /(^|\/)docs\/.*security.*\.(md|rst)$/i.test(file);
6903
+ }
6904
+ function isFreshnessRatableAuditFile(file) {
6905
+ return isAuditFile(file) && !isSecurityPolicyOnlyAuditFile(file);
6906
+ }
6907
+ function isIgnoredScanFile(file) {
6908
+ return /(^|\/)(package-lock\.json|pnpm-lock\.yaml|yarn\.lock|README\.md|CHANGELOG\.md)$/.test(file) || isEnvTemplatePath(file);
6909
+ }
6910
+ function findRootPackageJson(repoFiles) {
6911
+ return repoFiles.includes("package.json") ? "package.json" : null;
6912
+ }
6913
+ function isRegularFile(path) {
6914
+ try {
6915
+ return statSync(path).isFile();
6916
+ } catch {
6917
+ return false;
6918
+ }
6919
+ }
6920
+ function fileContains(repoPath, file, pattern) {
6921
+ const fullPath = join(repoPath, file);
6922
+ if (!isRegularFile(fullPath)) return false;
6923
+ return pattern.test(readFileSync(fullPath, "utf8"));
6924
+ }
6925
+ function fileContainsCommittedSecret(repoPath, file) {
6926
+ const fullPath = join(repoPath, file);
6927
+ if (!isRegularFile(fullPath)) return false;
6928
+ return containsRealSecret(readFileSync(fullPath, "utf8"));
6929
+ }
6930
+ function containsRealSecret(contents) {
6931
+ SECRET_ASSIGNMENT_PATTERN.lastIndex = 0;
6932
+ for (const match of contents.matchAll(SECRET_ASSIGNMENT_PATTERN)) {
6933
+ const rawValue = match[1];
6934
+ if (!rawValue) continue;
6935
+ const value = rawValue.replace(/[,;)]$/, "");
6936
+ if (isPlaceholderSecretValue(value)) continue;
6937
+ if (looksLikeSecretValue(value)) return true;
6938
+ }
6939
+ return false;
6940
+ }
6941
+ function collectHistorySecretEvidence(repoPath) {
6942
+ const historyEntries = readCredentialHistoryEntries(repoPath);
6943
+ let scannedFiles = 0;
6944
+ let envPathEvidence = null;
6945
+ for (const entry of historyEntries) {
6946
+ if (scannedFiles >= HISTORY_SECRET_SCAN_CREDENTIAL_BLOB_LIMIT) {
6947
+ return { evidence: null, envPathEvidence, truncated: true };
6948
+ }
6949
+ scannedFiles += 1;
6950
+ const contents = readGitBlob(repoPath, entry.commit, entry.path);
6951
+ if (!contents) continue;
6952
+ if (containsRealSecret(contents)) {
6953
+ return {
6954
+ evidence: {
6955
+ kind: "secret_scan",
6956
+ label: "Committed secret in recent git history",
6957
+ path: entry.path,
6958
+ contentHash: entry.commit
6959
+ },
6960
+ envPathEvidence,
6961
+ truncated: false
6962
+ };
6963
+ }
6964
+ if (!envPathEvidence && isEnvHistoryPath(entry.path)) {
6965
+ envPathEvidence = {
6966
+ kind: "secret_scan",
6967
+ label: ".env file (not a template) tracked in git history; no confirmed secret value found",
6968
+ path: entry.path,
6969
+ contentHash: entry.commit
6970
+ };
6971
+ }
6972
+ }
6973
+ return { evidence: null, envPathEvidence, truncated: false };
6974
+ }
6975
+ function readCredentialHistoryEntries(repoPath) {
6976
+ const entries = [];
6977
+ const seen = /* @__PURE__ */ new Set();
6978
+ const appendEntry = (entry) => {
6979
+ const key = `${entry.commit}:${entry.path}`;
6980
+ if (seen.has(key)) return;
6981
+ seen.add(key);
6982
+ entries.push(entry);
6983
+ };
6984
+ try {
6985
+ const commits = execFileSync("git", ["rev-list", "--all"], {
6986
+ cwd: repoPath,
6987
+ encoding: "utf8",
6988
+ stdio: ["ignore", "pipe", "ignore"]
6989
+ });
6990
+ const output = execFileSync(
6991
+ "git",
6992
+ [
6993
+ "diff-tree",
6994
+ "--stdin",
6995
+ "--root",
6996
+ "--name-only",
6997
+ "-r",
6998
+ "--diff-filter=AM",
6999
+ "--pretty=format:commit:%H"
7000
+ ],
7001
+ {
7002
+ cwd: repoPath,
7003
+ encoding: "utf8",
7004
+ input: commits,
7005
+ stdio: ["pipe", "pipe", "ignore"]
7006
+ }
7007
+ );
7008
+ let currentCommit = null;
7009
+ for (const line of output.split("\n")) {
7010
+ if (line.startsWith("commit:")) {
7011
+ currentCommit = line.slice("commit:".length);
7012
+ continue;
7013
+ }
7014
+ const path = line.trim();
7015
+ if (!currentCommit || !path) continue;
7016
+ if (!isCredentialHistoryPath(path)) continue;
7017
+ appendEntry({ commit: currentCommit, path });
7018
+ }
7019
+ } catch {
7020
+ }
7021
+ for (const entry of readDeletedCredentialHistoryEntries(repoPath)) {
7022
+ appendEntry(entry);
7023
+ }
7024
+ return entries;
7025
+ }
7026
+ function readDeletedCredentialHistoryEntries(repoPath) {
7027
+ const deletedPaths = readDeletedCredentialHistoryPaths(repoPath);
7028
+ const entries = [];
7029
+ const seen = /* @__PURE__ */ new Set();
7030
+ for (const path of deletedPaths) {
7031
+ for (const commit of readHistoryCommitsForPath(repoPath, path)) {
7032
+ const key = `${commit}:${path}`;
7033
+ if (seen.has(key)) continue;
7034
+ seen.add(key);
7035
+ entries.push({ commit, path });
7036
+ }
7037
+ }
7038
+ return entries;
7039
+ }
7040
+ function readDeletedCredentialHistoryPaths(repoPath) {
7041
+ try {
7042
+ const output = execFileSync(
7043
+ "git",
7044
+ ["log", "--all", "--diff-filter=D", "--name-status", "--format=commit:%H"],
7045
+ {
7046
+ cwd: repoPath,
7047
+ encoding: "utf8",
7048
+ stdio: ["ignore", "pipe", "ignore"]
7049
+ }
7050
+ );
7051
+ const paths = [];
7052
+ const seen = /* @__PURE__ */ new Set();
7053
+ for (const line of output.split("\n")) {
7054
+ if (!line.startsWith("D ")) continue;
7055
+ const path = line.slice(2).trim();
7056
+ if (!path || seen.has(path)) continue;
7057
+ if (!isCredentialHistoryPath(path)) continue;
7058
+ seen.add(path);
7059
+ paths.push(path);
7060
+ }
7061
+ return paths;
7062
+ } catch {
7063
+ return [];
7064
+ }
7065
+ }
7066
+ function readHistoryCommitsForPath(repoPath, path) {
7067
+ try {
7068
+ const output = execFileSync(
7069
+ "git",
7070
+ ["log", "--all", "--diff-filter=AM", "--format=%H", "--", path],
7071
+ {
7072
+ cwd: repoPath,
7073
+ encoding: "utf8",
7074
+ stdio: ["ignore", "pipe", "ignore"]
7075
+ }
7076
+ );
7077
+ return output.split("\n").map((line) => line.trim()).filter((line) => /^[0-9a-f]{40}$/i.test(line));
7078
+ } catch {
7079
+ return [];
7080
+ }
7081
+ }
7082
+ function isCredentialHistoryPath(path) {
7083
+ if (isHardExcludedPath(path)) return false;
7084
+ const lowerPath = path.toLowerCase();
7085
+ const basename3 = lowerPath.split("/").at(-1) ?? lowerPath;
7086
+ if (/\.env(?:\.|$)/.test(basename3)) {
7087
+ return true;
7088
+ }
7089
+ return lowerPath.includes("secret") || lowerPath.includes("credential") || basename3.endsWith(".pem") || basename3.endsWith(".key") || basename3 === "id_rsa" || basename3.endsWith(".p12") || basename3.endsWith(".pfx");
7090
+ }
7091
+ function isEnvHistoryPath(path) {
7092
+ if (isEnvTemplatePath(path)) return false;
7093
+ const basename3 = path.toLowerCase().split("/").at(-1) ?? path.toLowerCase();
7094
+ return /\.env(?:\.|$)/.test(basename3);
7095
+ }
7096
+ function readGitBlob(repoPath, commit, path) {
7097
+ try {
7098
+ return execFileSync("git", ["show", `${commit}:${path}`], {
7099
+ cwd: repoPath,
7100
+ encoding: "utf8",
7101
+ maxBuffer: 512e3,
7102
+ stdio: ["ignore", "pipe", "ignore"]
7103
+ });
7104
+ } catch {
7105
+ return null;
7106
+ }
7107
+ }
7108
+ var ALL_CAPS_SNAKE_PLACEHOLDER_PATTERN = /^[A-Z][A-Z0-9]*(?:_[A-Z0-9]+)+$/;
7109
+ function isPlaceholderSecretValue(value) {
7110
+ const normalized = value.trim().toLowerCase();
7111
+ return PLACEHOLDER_SECRET_PATTERN.test(normalized) || normalized.includes("your-") || normalized.includes("example") || ALL_CAPS_SNAKE_PLACEHOLDER_PATTERN.test(value.trim()) || isSyntheticFixtureSecretValue(normalized) || isFillerRunSecretValue(normalized);
7112
+ }
7113
+ function isFillerRunSecretValue(value) {
7114
+ const candidates = [value];
7115
+ const sepIdx = Math.max(value.lastIndexOf("_"), value.lastIndexOf("-"));
7116
+ if (sepIdx > 0 && sepIdx < value.length - 1) {
7117
+ candidates.push(value.slice(sepIdx + 1));
7118
+ }
7119
+ for (const body of candidates) {
7120
+ if (body.length < 8) continue;
7121
+ const counts = /* @__PURE__ */ new Map();
7122
+ for (const ch of body) counts.set(ch, (counts.get(ch) ?? 0) + 1);
7123
+ const distinct = counts.size;
7124
+ const maxRun = Math.max(...counts.values());
7125
+ if (distinct <= 2 && maxRun / body.length >= 0.8) return true;
8486
7126
  }
8487
7127
  return false;
8488
7128
  }
8489
- function isDependencyManifest(file) {
8490
- return /(^|\/)(package\.json|pyproject\.toml|requirements(?:[^/]*)?\.txt|go\.mod|Cargo\.toml|pom\.xml|build\.gradle|vcpkg\.json|Pipfile|CMakeLists\.txt|conanfile\.txt|conanfile\.py)$/.test(
8491
- file
8492
- );
8493
- }
8494
- function isLockfile(file) {
8495
- return /(^|\/)(pnpm-lock\.yaml|package-lock\.json|yarn\.lock|uv\.lock|poetry\.lock|go\.sum|Cargo\.lock|Pipfile\.lock|composer\.lock|conan\.lock|vcpkg\.lock\.json)$/.test(
8496
- file
8497
- );
8498
- }
8499
- function isDependencyUpdateConfig(file) {
8500
- return /(^|\/)(renovate\.json|renovate\.json5|\.renovaterc\.json|dependabot\.ya?ml)$/.test(file) || /^\.github\/dependabot\.ya?ml$/.test(file);
7129
+ function isSyntheticFixtureSecretValue(value) {
7130
+ return value.includes("abcdefghijklmnopqrstuvwxyz") || value.includes("0123456789abcdefghijklmnopqrstuvwxyz") || value.includes("abcdefghijklmnopqrstuvwxyz0123456789") || value.includes("abcdefghijklmnopqrst");
8501
7131
  }
8502
- function packageJsonHasAuditScript(repoPath, manifest) {
7132
+ function hasSuspiciousDependencies(repoPath, manifest) {
8503
7133
  if (!manifest.endsWith("package.json")) return false;
8504
- const scripts = readPackageScripts(join3(repoPath, manifest));
8505
- return [...scripts.values()].some(
8506
- (script) => /\b(audit|npm audit|pnpm audit|yarn audit)\b/i.test(script)
8507
- );
8508
- }
8509
- function packageJsonHasHeavyTestDependency(repoPath, manifest) {
8510
- const fullPath = join3(repoPath, manifest);
7134
+ const fullPath = join(repoPath, manifest);
8511
7135
  if (!isRegularFile(fullPath)) return false;
8512
- const parsed = parseJsonObject(readFileSync6(fullPath, "utf8"));
7136
+ const parsed = parseJsonObject(readFileSync(fullPath, "utf8"));
8513
7137
  if (!parsed) return false;
8514
- const names = [
8515
- ...Object.keys(isRecord(parsed.dependencies) ? parsed.dependencies : {}),
8516
- ...Object.keys(isRecord(parsed.devDependencies) ? parsed.devDependencies : {})
8517
- ];
8518
- return names.some((name) => HEAVY_TEST_DEPENDENCY_NAME_PATTERN.test(name));
7138
+ const dependencies = isRecord(parsed.dependencies) ? parsed.dependencies : {};
7139
+ const devDependencies = isRecord(parsed.devDependencies) ? parsed.devDependencies : {};
7140
+ const names = [...Object.keys(dependencies), ...Object.keys(devDependencies)];
7141
+ return names.some(
7142
+ (name) => /^(todo|fake|placeholder|example)-|does-not-exist| hallucinated/i.test(name)
7143
+ );
8519
7144
  }
8520
- function isImplementationFile(file) {
8521
- return /(^|\/)(src|app|lib|packages|cmd|include|source|Sources)\//.test(file) && /\.(ts|tsx|js|jsx|py|go|rs|java|rb|cpp|cc|cxx|c|h|hpp|kt|swift|php)$/.test(file);
7145
+ function readRecentCommits(repoPath) {
7146
+ try {
7147
+ const output = execFileSync("git", ["log", "--max-count=12", "--format=%H%x00%s"], {
7148
+ cwd: repoPath,
7149
+ encoding: "utf8",
7150
+ stdio: ["ignore", "pipe", "ignore"]
7151
+ }).trim();
7152
+ if (!output) return [];
7153
+ return output.split("\n").map((line) => {
7154
+ const [sha = "", subject = ""] = line.split("\0");
7155
+ return { sha, subject };
7156
+ }).filter((commit) => commit.sha.length >= 7);
7157
+ } catch {
7158
+ return [];
7159
+ }
8522
7160
  }
8523
- function isAuditFile(file) {
8524
- return (
8525
- // goal_cejel_calibration_fix_with_strict_gate_2026-07-06: mature OSS repos document the
8526
- // same audit-trail practice under different filenames/extensions than Alfred's own
8527
- // conventions (Flask ships CHANGES.rst, not CHANGELOG.md) — recognize the common OSS
8528
- // release-notes/security-policy/provenance equivalents so real audit-trail artifacts are
8529
- // credited instead of silently missing the pattern.
8530
- /(^|\/)(CHANGELOG|CHANGES|HISTORY|NEWS|RELEASE_NOTES|RELEASES|SECURITY|AUDIT|STATUS)\.(md|rst|txt)$/i.test(
8531
- file
8532
- ) || /(^|\/)docs\/.*(audit|runbook|incident|changelog|security).*\.(md|rst)$/i.test(file) || // Provenance/signed-release tooling config is itself audit-trail evidence (a repo that
8533
- // wires SLSA/cosign attestation or CITATION.cff is documenting release provenance).
8534
- /(^|\/)CITATION\.cff$/i.test(file)
7161
+ function readPackageScripts(packageJsonPath) {
7162
+ if (!isRegularFile(packageJsonPath)) return /* @__PURE__ */ new Map();
7163
+ const parsed = parseJsonObject(readFileSync(packageJsonPath, "utf8"));
7164
+ const scripts = parsed?.scripts;
7165
+ if (!isRecord(scripts)) return /* @__PURE__ */ new Map();
7166
+ return new Map(
7167
+ Object.entries(scripts).filter(
7168
+ (entry) => typeof entry[1] === "string"
7169
+ )
8535
7170
  );
8536
7171
  }
8537
- function isSecurityPolicyOnlyAuditFile(file) {
8538
- return /(^|\/)SECURITY\.(md|rst|txt)$/i.test(file) || /(^|\/)docs\/.*security.*\.(md|rst)$/i.test(file);
7172
+ function evidenceForRelative(repoPath, path, kind, label) {
7173
+ const fullPath = join(repoPath, path);
7174
+ const contents = isRegularFile(fullPath) ? readFileSync(fullPath, "utf8") : "";
7175
+ return {
7176
+ kind,
7177
+ label,
7178
+ path,
7179
+ ...contents ? {
7180
+ line: firstMeaningfulLine(contents),
7181
+ contentHash: createHash2("sha256").update(contents).digest("hex")
7182
+ } : {}
7183
+ };
8539
7184
  }
8540
- function isFreshnessRatableAuditFile(file) {
8541
- return isAuditFile(file) && !isSecurityPolicyOnlyAuditFile(file);
7185
+ function evidenceForRelativeAtLine(repoPath, path, kind, label, line) {
7186
+ const fullPath = join(repoPath, path);
7187
+ const contents = isRegularFile(fullPath) ? readFileSync(fullPath, "utf8") : "";
7188
+ return {
7189
+ kind,
7190
+ label,
7191
+ path,
7192
+ line,
7193
+ ...contents ? { contentHash: createHash2("sha256").update(contents).digest("hex") } : {}
7194
+ };
8542
7195
  }
8543
- function isIgnoredScanFile(file) {
8544
- return /(^|\/)(package-lock\.json|pnpm-lock\.yaml|yarn\.lock|README\.md|CHANGELOG\.md)$/.test(file) || isEnvTemplatePath(file);
7196
+ function metric(name, label, value, max, weight, unit, description, kind) {
7197
+ return {
7198
+ name,
7199
+ label,
7200
+ value: Math.max(0, value),
7201
+ max,
7202
+ ...kind ? { kind } : {},
7203
+ weight,
7204
+ unit,
7205
+ description
7206
+ };
8545
7207
  }
8546
- function findRootPackageJson(repoFiles) {
8547
- return repoFiles.includes("package.json") ? "package.json" : null;
7208
+ function firstMeaningfulLine(contents) {
7209
+ const lines = contents.split("\n");
7210
+ const index = lines.findIndex((line) => line.trim().length > 0);
7211
+ return index === -1 ? 1 : index + 1;
8548
7212
  }
8549
- function isRegularFile(path) {
7213
+ function readGitHead(repoPath) {
7214
+ try {
7215
+ return execFileSync("git", ["rev-parse", "HEAD"], {
7216
+ cwd: repoPath,
7217
+ encoding: "utf8",
7218
+ stdio: ["ignore", "pipe", "ignore"]
7219
+ }).trim();
7220
+ } catch {
7221
+ return null;
7222
+ }
7223
+ }
7224
+ function hasEnvPathInGitHistory(repoPath) {
8550
7225
  try {
8551
- return statSync2(path).isFile();
7226
+ const output = execFileSync(
7227
+ "git",
7228
+ ["log", "--all", "--diff-filter=AM", "--name-only", "--format="],
7229
+ {
7230
+ cwd: repoPath,
7231
+ encoding: "utf8",
7232
+ stdio: ["ignore", "pipe", "ignore"],
7233
+ maxBuffer: 512e3
7234
+ }
7235
+ ).trim();
7236
+ if (!output) return false;
7237
+ return output.split("\n").some((p) => /(?:^|\/)\.env(?:\.|$)/i.test(p.trim()));
8552
7238
  } catch {
8553
7239
  return false;
8554
7240
  }
8555
7241
  }
8556
- function fileContains(repoPath, file, pattern) {
8557
- const fullPath = join3(repoPath, file);
8558
- if (!isRegularFile(fullPath)) return false;
8559
- return pattern.test(readFileSync6(fullPath, "utf8"));
7242
+
7243
+ // src/witan/public-scan.ts
7244
+ import { resolve as resolve2 } from "path";
7245
+
7246
+ // src/witan/ingest.ts
7247
+ import { readFileSync as readFileSync5, readdirSync as readdirSync2 } from "fs";
7248
+ import { join as join2 } from "path";
7249
+
7250
+ // src/witan/finding-limits.ts
7251
+ var RULE_ID_MAX = 200;
7252
+ var MESSAGE_MAX = 500;
7253
+ var LOCATION_MAX = 700;
7254
+ function clamp(value, max) {
7255
+ if (value.length <= max) return value;
7256
+ const ellipsis = "...";
7257
+ return `${value.slice(0, Math.max(max - ellipsis.length, 0))}${ellipsis}`;
8560
7258
  }
8561
- function fileContainsCommittedSecret(repoPath, file) {
8562
- const fullPath = join3(repoPath, file);
8563
- if (!isRegularFile(fullPath)) return false;
8564
- return containsRealSecret(readFileSync6(fullPath, "utf8"));
7259
+ function clampFinding(finding) {
7260
+ return {
7261
+ ...finding,
7262
+ ruleId: clamp(finding.ruleId, RULE_ID_MAX),
7263
+ message: clamp(finding.message, MESSAGE_MAX),
7264
+ ...finding.location ? { location: clamp(finding.location, LOCATION_MAX) } : {}
7265
+ };
8565
7266
  }
8566
- function containsRealSecret(contents) {
8567
- SECRET_ASSIGNMENT_PATTERN.lastIndex = 0;
8568
- for (const match of contents.matchAll(SECRET_ASSIGNMENT_PATTERN)) {
8569
- const rawValue = match[1];
8570
- if (!rawValue) continue;
8571
- const value = rawValue.replace(/[,;)]$/, "");
8572
- if (isPlaceholderSecretValue(value)) continue;
8573
- if (looksLikeSecretValue(value)) return true;
7267
+
7268
+ // src/witan/generic-adapter.ts
7269
+ import { readFileSync as readFileSync2 } from "fs";
7270
+ var VALID_DIMENSIONS = /* @__PURE__ */ new Set([
7271
+ "A1",
7272
+ "A2",
7273
+ "A3",
7274
+ "A4",
7275
+ "A5",
7276
+ "B1",
7277
+ "B2",
7278
+ "B3",
7279
+ "B4",
7280
+ "B5",
7281
+ "B6"
7282
+ ]);
7283
+ var VALID_SEVERITIES = /* @__PURE__ */ new Set(["critical", "warning", "info"]);
7284
+ function isGenericSignalDocument(raw) {
7285
+ if (!raw || typeof raw !== "object" || Array.isArray(raw)) return false;
7286
+ const doc = raw;
7287
+ return typeof doc.tool === "string" && doc.tool.length > 0 && Array.isArray(doc.signals);
7288
+ }
7289
+ function parseGenericJson(raw) {
7290
+ if (!isGenericSignalDocument(raw)) return [];
7291
+ const source = raw.tool ?? "unknown";
7292
+ const signals = [];
7293
+ for (const signal of raw.signals ?? []) {
7294
+ const dimension = signal.dimension;
7295
+ if (!dimension || !VALID_DIMENSIONS.has(dimension)) continue;
7296
+ const weight = typeof signal.weight === "number" && Number.isFinite(signal.weight) ? Math.min(Math.max(signal.weight, 0), 1) : 0.5;
7297
+ const findings = [];
7298
+ for (const finding of signal.findings ?? []) {
7299
+ const severity = finding.severity;
7300
+ if (!severity || !VALID_SEVERITIES.has(severity)) continue;
7301
+ const ruleId = finding.ruleId ?? "unknown";
7302
+ findings.push({
7303
+ ruleId,
7304
+ severity,
7305
+ message: finding.message ?? ruleId,
7306
+ ...finding.location ? { location: finding.location } : {}
7307
+ });
7308
+ }
7309
+ if (findings.length === 0) continue;
7310
+ signals.push({ source, dimension, weight, findings });
7311
+ }
7312
+ return signals;
7313
+ }
7314
+
7315
+ // src/witan/sarif-adapter.ts
7316
+ import { readFileSync as readFileSync3 } from "fs";
7317
+ var DIMENSION_RULES = [
7318
+ // A2 — injection / secrets / auth (high weight)
7319
+ {
7320
+ pattern: /sql[- _]?inject|cwe-89|sqli|command[- _]?inject|cwe-78|os[- _]?cmd|rce|remote[- _]?code/i,
7321
+ dimension: "A2",
7322
+ weight: 0.9
7323
+ },
7324
+ {
7325
+ pattern: /secret|credential|api[- _]?key|password[- _]?leak|hardcoded[- _]?(token|key|secret)|cwe-259|cwe-798/i,
7326
+ dimension: "A2",
7327
+ weight: 0.9
7328
+ },
7329
+ {
7330
+ pattern: /path[- _]?traversal|directory[- _]?traversal|cwe-22|lfi|rfi/i,
7331
+ dimension: "A2",
7332
+ weight: 0.8
7333
+ },
7334
+ {
7335
+ pattern: /ssrf|server[- _]?side[- _]?request[- _]?forg|cwe-918/i,
7336
+ dimension: "A2",
7337
+ weight: 0.8
7338
+ },
7339
+ {
7340
+ pattern: /xxe|xml[- _]?external[- _]?entity|cwe-611/i,
7341
+ dimension: "A2",
7342
+ weight: 0.8
7343
+ },
7344
+ {
7345
+ pattern: /auth[- _]?bypass|broken[- _]?auth|missing[- _]?auth|cwe-287|cwe-306|cwe-863|cwe-862/i,
7346
+ dimension: "A2",
7347
+ weight: 0.7
7348
+ },
7349
+ {
7350
+ pattern: /xss|cross[- _]?site[- _]?script|cwe-79/i,
7351
+ dimension: "A2",
7352
+ weight: 0.6
7353
+ },
7354
+ // A4 — dependency vulnerabilities
7355
+ {
7356
+ pattern: /cve-\d{4}-\d+|supply[- _]?chain|depend[a-z]*[- _]?vulner|outdated[- _]?depend|deprecated[- _]?package/i,
7357
+ dimension: "A4",
7358
+ weight: 0.8
7359
+ },
7360
+ {
7361
+ pattern: /npm[- _]?audit|yarn[- _]?audit|pnpm[- _]?audit|pip[- _]?audit|cargo[- _]?audit/i,
7362
+ dimension: "A4",
7363
+ weight: 0.7
7364
+ },
7365
+ // A3 — production readiness / insecure config
7366
+ {
7367
+ pattern: /insecure[- _]?tls|weak[- _]?cipher|tls[- _]?version|http[- _]?strict|hsts|csp[- _]?missing|cwe-326|cwe-327/i,
7368
+ dimension: "A3",
7369
+ weight: 0.5
7370
+ },
7371
+ {
7372
+ pattern: /error[- _]?handl|unhandled[- _]?exception|crash|uncaught|stacktrace[- _]?leak/i,
7373
+ dimension: "A3",
7374
+ weight: 0.4
7375
+ },
7376
+ {
7377
+ pattern: /debug[- _]?mode|dev[- _]?endpoint|staging[- _]?secret/i,
7378
+ dimension: "A3",
7379
+ weight: 0.4
7380
+ },
7381
+ // A1 — test integrity (low weight; SARIF rarely surfaces this)
7382
+ {
7383
+ pattern: /skipped[- _]?test|hollow[- _]?test|empty[- _]?assert|no[- _]?assertion/i,
7384
+ dimension: "A1",
7385
+ weight: 0.2
8574
7386
  }
8575
- return false;
7387
+ ];
7388
+ var DEFAULT_DIMENSION = "A2";
7389
+ var DEFAULT_WEIGHT = 0.3;
7390
+ var DROP_LEVEL = /* @__PURE__ */ new Set(["none"]);
7391
+ function mapLevel(level) {
7392
+ if (!level || DROP_LEVEL.has(level)) return null;
7393
+ if (level === "error") return "critical";
7394
+ if (level === "warning") return "warning";
7395
+ return "info";
8576
7396
  }
8577
- function collectHistorySecretEvidence(repoPath) {
8578
- const historyEntries = readCredentialHistoryEntries(repoPath);
8579
- let scannedFiles = 0;
8580
- let envPathEvidence = null;
8581
- for (const entry of historyEntries) {
8582
- if (scannedFiles >= HISTORY_SECRET_SCAN_CREDENTIAL_BLOB_LIMIT) {
8583
- return { evidence: null, envPathEvidence, truncated: true };
8584
- }
8585
- scannedFiles += 1;
8586
- const contents = readGitBlob(repoPath, entry.commit, entry.path);
8587
- if (!contents) continue;
8588
- if (containsRealSecret(contents)) {
8589
- return {
8590
- evidence: {
8591
- kind: "secret_scan",
8592
- label: "Committed secret in recent git history",
8593
- path: entry.path,
8594
- contentHash: entry.commit
8595
- },
8596
- envPathEvidence,
8597
- truncated: false
8598
- };
8599
- }
8600
- if (!envPathEvidence && isEnvHistoryPath(entry.path)) {
8601
- envPathEvidence = {
8602
- kind: "secret_scan",
8603
- label: ".env file (not a template) tracked in git history; no confirmed secret value found",
8604
- path: entry.path,
8605
- contentHash: entry.commit
8606
- };
7397
+ function mapRuleToDimension(ruleId, rules) {
7398
+ for (const rule of rules) {
7399
+ if (rule.pattern.test(ruleId)) {
7400
+ return { dimension: rule.dimension, weight: rule.weight };
8607
7401
  }
8608
7402
  }
8609
- return { evidence: null, envPathEvidence, truncated: false };
7403
+ return { dimension: DEFAULT_DIMENSION, weight: DEFAULT_WEIGHT };
8610
7404
  }
8611
- function readCredentialHistoryEntries(repoPath) {
8612
- const entries = [];
7405
+ function renderLocation(result) {
7406
+ const loc = result.locations?.[0]?.physicalLocation;
7407
+ if (!loc) return void 0;
7408
+ const uri = loc.artifactLocation?.uri;
7409
+ const line = loc.region?.startLine;
7410
+ if (!uri) return void 0;
7411
+ return line != null ? `${uri}:${line}` : uri;
7412
+ }
7413
+ function dedupeFindings(findings) {
8613
7414
  const seen = /* @__PURE__ */ new Set();
8614
- const appendEntry = (entry) => {
8615
- const key = `${entry.commit}:${entry.path}`;
8616
- if (seen.has(key)) return;
7415
+ return findings.filter((f) => {
7416
+ const key = `${f.ruleId}|${f.severity}|${f.location ?? ""}`;
7417
+ if (seen.has(key)) return false;
8617
7418
  seen.add(key);
8618
- entries.push(entry);
8619
- };
8620
- try {
8621
- const commits = execFileSync("git", ["rev-list", "--all"], {
8622
- cwd: repoPath,
8623
- encoding: "utf8",
8624
- stdio: ["ignore", "pipe", "ignore"]
8625
- });
8626
- const output = execFileSync(
8627
- "git",
8628
- [
8629
- "diff-tree",
8630
- "--stdin",
8631
- "--root",
8632
- "--name-only",
8633
- "-r",
8634
- "--diff-filter=AM",
8635
- "--pretty=format:commit:%H"
8636
- ],
8637
- {
8638
- cwd: repoPath,
8639
- encoding: "utf8",
8640
- input: commits,
8641
- stdio: ["pipe", "pipe", "ignore"]
8642
- }
8643
- );
8644
- let currentCommit = null;
8645
- for (const line of output.split("\n")) {
8646
- if (line.startsWith("commit:")) {
8647
- currentCommit = line.slice("commit:".length);
8648
- continue;
8649
- }
8650
- const path = line.trim();
8651
- if (!currentCommit || !path) continue;
8652
- if (!isCredentialHistoryPath(path)) continue;
8653
- appendEntry({ commit: currentCommit, path });
8654
- }
8655
- } catch {
8656
- }
8657
- for (const entry of readDeletedCredentialHistoryEntries(repoPath)) {
8658
- appendEntry(entry);
8659
- }
8660
- return entries;
7419
+ return true;
7420
+ });
8661
7421
  }
8662
- function readDeletedCredentialHistoryEntries(repoPath) {
8663
- const deletedPaths = readDeletedCredentialHistoryPaths(repoPath);
8664
- const entries = [];
8665
- const seen = /* @__PURE__ */ new Set();
8666
- for (const path of deletedPaths) {
8667
- for (const commit of readHistoryCommitsForPath(repoPath, path)) {
8668
- const key = `${commit}:${path}`;
8669
- if (seen.has(key)) continue;
8670
- seen.add(key);
8671
- entries.push({ commit, path });
7422
+ function parseSarifJson(raw, extraDimensionRules) {
7423
+ if (!raw || typeof raw !== "object" || Array.isArray(raw)) return [];
7424
+ const dimensionRules = extraDimensionRules ? [...DIMENSION_RULES, ...extraDimensionRules] : DIMENSION_RULES;
7425
+ const doc = raw;
7426
+ if (!Array.isArray(doc.runs)) return [];
7427
+ const buckets = /* @__PURE__ */ new Map();
7428
+ for (const run of doc.runs) {
7429
+ const driverName = run.tool?.driver?.name ?? "unknown";
7430
+ const source = `sarif:${driverName}`;
7431
+ const ruleDefaultLevels = /* @__PURE__ */ new Map();
7432
+ for (const rule of run.tool?.driver?.rules ?? []) {
7433
+ if (rule.id && rule.defaultConfiguration?.level) {
7434
+ ruleDefaultLevels.set(rule.id, rule.defaultConfiguration.level);
7435
+ }
8672
7436
  }
8673
- }
8674
- return entries;
8675
- }
8676
- function readDeletedCredentialHistoryPaths(repoPath) {
8677
- try {
8678
- const output = execFileSync(
8679
- "git",
8680
- ["log", "--all", "--diff-filter=D", "--name-status", "--format=commit:%H"],
8681
- {
8682
- cwd: repoPath,
8683
- encoding: "utf8",
8684
- stdio: ["ignore", "pipe", "ignore"]
7437
+ for (const result of run.results ?? []) {
7438
+ const ruleId = result.ruleId ?? "unknown";
7439
+ const effectiveLevel = result.level ?? ruleDefaultLevels.get(ruleId) ?? "warning";
7440
+ const severity = mapLevel(effectiveLevel);
7441
+ if (!severity) continue;
7442
+ const message = result.message?.text ?? ruleId;
7443
+ const location = renderLocation(result);
7444
+ const { dimension, weight } = mapRuleToDimension(ruleId, dimensionRules);
7445
+ const bucketKey = `${source}|${dimension}`;
7446
+ if (!buckets.has(bucketKey)) {
7447
+ buckets.set(bucketKey, { source, dimension, weight, findings: [] });
8685
7448
  }
8686
- );
8687
- const paths = [];
8688
- const seen = /* @__PURE__ */ new Set();
8689
- for (const line of output.split("\n")) {
8690
- if (!line.startsWith("D ")) continue;
8691
- const path = line.slice(2).trim();
8692
- if (!path || seen.has(path)) continue;
8693
- if (!isCredentialHistoryPath(path)) continue;
8694
- seen.add(path);
8695
- paths.push(path);
7449
+ buckets.get(bucketKey)?.findings.push({ ruleId, severity, message, ...location ? { location } : {} });
8696
7450
  }
8697
- return paths;
8698
- } catch {
8699
- return [];
8700
7451
  }
7452
+ return Array.from(buckets.values()).map(({ source, dimension, weight, findings }) => ({
7453
+ source,
7454
+ dimension,
7455
+ weight,
7456
+ findings: dedupeFindings(findings)
7457
+ }));
8701
7458
  }
8702
- function readHistoryCommitsForPath(repoPath, path) {
8703
- try {
8704
- const output = execFileSync(
8705
- "git",
8706
- ["log", "--all", "--diff-filter=AM", "--format=%H", "--", path],
8707
- {
8708
- cwd: repoPath,
8709
- encoding: "utf8",
8710
- stdio: ["ignore", "pipe", "ignore"]
8711
- }
8712
- );
8713
- return output.split("\n").map((line) => line.trim()).filter((line) => /^[0-9a-f]{40}$/i.test(line));
8714
- } catch {
8715
- return [];
8716
- }
7459
+
7460
+ // src/witan/scorecard-adapter.ts
7461
+ import { readFileSync as readFileSync4 } from "fs";
7462
+ var CHECK_RULES = {
7463
+ // B2 — PR outcome traceability
7464
+ "Branch-Protection": { dimension: "B2", weight: 0.8 },
7465
+ "Code-Review": { dimension: "B2", weight: 0.7 },
7466
+ // B3 — CI and QA discipline
7467
+ "Dangerous-Workflow": { dimension: "B3", weight: 0.9 },
7468
+ "Token-Permissions": { dimension: "B3", weight: 0.8 },
7469
+ "CI-Tests": { dimension: "B3", weight: 0.7 },
7470
+ Maintained: { dimension: "B3", weight: 0.3 },
7471
+ // B4 — audit trail / release integrity
7472
+ "Signed-Releases": { dimension: "B4", weight: 0.7 },
7473
+ Packaging: { dimension: "B4", weight: 0.4 },
7474
+ "Security-Policy": { dimension: "B4", weight: 0.4 },
7475
+ // A4 — dependency hygiene
7476
+ Vulnerabilities: { dimension: "A4", weight: 0.9 },
7477
+ "Pinned-Dependencies": { dimension: "A4", weight: 0.8 },
7478
+ "Dependency-Update-Tool": { dimension: "A4", weight: 0.6 },
7479
+ // A2 — data-layer / static analysis
7480
+ SAST: { dimension: "A2", weight: 0.7 },
7481
+ "Binary-Artifacts": { dimension: "A2", weight: 0.6 },
7482
+ // A1 — test integrity
7483
+ Fuzzing: { dimension: "A1", weight: 0.3 }
7484
+ };
7485
+ function mapScoreToSeverity(score) {
7486
+ if (score == null || Number.isNaN(score)) return null;
7487
+ if (score < 0) return null;
7488
+ if (score >= 10) return null;
7489
+ if (score <= 3) return "critical";
7490
+ if (score <= 6) return "warning";
7491
+ return "info";
8717
7492
  }
8718
- function isCredentialHistoryPath(path) {
8719
- if (isHardExcludedPath(path)) return false;
8720
- const lowerPath = path.toLowerCase();
8721
- const basename4 = lowerPath.split("/").at(-1) ?? lowerPath;
8722
- if (/\.env(?:\.|$)/.test(basename4)) {
7493
+ function dedupeFindings2(findings) {
7494
+ const seen = /* @__PURE__ */ new Set();
7495
+ return findings.filter((f) => {
7496
+ const key = `${f.ruleId}|${f.severity}|${f.location ?? ""}`;
7497
+ if (seen.has(key)) return false;
7498
+ seen.add(key);
8723
7499
  return true;
8724
- }
8725
- return lowerPath.includes("secret") || lowerPath.includes("credential") || basename4.endsWith(".pem") || basename4.endsWith(".key") || basename4 === "id_rsa" || basename4.endsWith(".p12") || basename4.endsWith(".pfx");
8726
- }
8727
- function isEnvHistoryPath(path) {
8728
- if (isEnvTemplatePath(path)) return false;
8729
- const basename4 = path.toLowerCase().split("/").at(-1) ?? path.toLowerCase();
8730
- return /\.env(?:\.|$)/.test(basename4);
7500
+ });
8731
7501
  }
8732
- function readGitBlob(repoPath, commit, path) {
8733
- try {
8734
- return execFileSync("git", ["show", `${commit}:${path}`], {
8735
- cwd: repoPath,
8736
- encoding: "utf8",
8737
- maxBuffer: 512e3,
8738
- stdio: ["ignore", "pipe", "ignore"]
7502
+ function parseScorecardJson(raw) {
7503
+ if (!raw || typeof raw !== "object" || Array.isArray(raw)) return [];
7504
+ const doc = raw;
7505
+ if (!Array.isArray(doc.checks)) return [];
7506
+ const buckets = /* @__PURE__ */ new Map();
7507
+ for (const check of doc.checks) {
7508
+ const name = check.name;
7509
+ if (!name) continue;
7510
+ const rule = CHECK_RULES[name];
7511
+ if (!rule) continue;
7512
+ const severity = mapScoreToSeverity(check.score);
7513
+ if (!severity) continue;
7514
+ const scoreText = typeof check.score === "number" ? `${check.score}/10` : "n/a";
7515
+ const message = `${name} (Scorecard ${scoreText}): ${check.reason ?? "weakness detected"}`.slice(0, 500);
7516
+ const location = check.documentation?.url;
7517
+ const bucket = buckets.get(rule.dimension) ?? { weight: 0, findings: [] };
7518
+ bucket.weight = Math.max(bucket.weight, rule.weight);
7519
+ bucket.findings.push({
7520
+ ruleId: `scorecard:${name}`,
7521
+ severity,
7522
+ message,
7523
+ ...location ? { location } : {}
8739
7524
  });
8740
- } catch {
8741
- return null;
7525
+ buckets.set(rule.dimension, bucket);
8742
7526
  }
7527
+ return Array.from(buckets.entries()).map(([dimension, { weight, findings }]) => ({
7528
+ source: "scorecard",
7529
+ dimension,
7530
+ weight,
7531
+ findings: dedupeFindings2(findings)
7532
+ }));
8743
7533
  }
8744
- var ALL_CAPS_SNAKE_PLACEHOLDER_PATTERN = /^[A-Z][A-Z0-9]*(?:_[A-Z0-9]+)+$/;
8745
- function isPlaceholderSecretValue(value) {
8746
- const normalized = value.trim().toLowerCase();
8747
- return PLACEHOLDER_SECRET_PATTERN.test(normalized) || normalized.includes("your-") || normalized.includes("example") || ALL_CAPS_SNAKE_PLACEHOLDER_PATTERN.test(value.trim()) || isSyntheticFixtureSecretValue(normalized) || isFillerRunSecretValue(normalized);
7534
+
7535
+ // src/witan/ingest.ts
7536
+ function looksLikeSarif(raw) {
7537
+ if (!raw || typeof raw !== "object" || Array.isArray(raw)) return false;
7538
+ return Array.isArray(raw.runs);
8748
7539
  }
8749
- function isFillerRunSecretValue(value) {
8750
- const candidates = [value];
8751
- const sepIdx = Math.max(value.lastIndexOf("_"), value.lastIndexOf("-"));
8752
- if (sepIdx > 0 && sepIdx < value.length - 1) {
8753
- candidates.push(value.slice(sepIdx + 1));
7540
+ function looksLikeScorecard(raw) {
7541
+ if (!raw || typeof raw !== "object" || Array.isArray(raw)) return false;
7542
+ return Array.isArray(raw.checks);
7543
+ }
7544
+ function countRawEntries(raw) {
7545
+ const obj = raw;
7546
+ if (Array.isArray(obj.runs)) {
7547
+ return obj.runs.reduce((sum, run) => {
7548
+ const results = run.results;
7549
+ return sum + (Array.isArray(results) ? results.length : 0);
7550
+ }, 0);
8754
7551
  }
8755
- for (const body of candidates) {
8756
- if (body.length < 8) continue;
8757
- const counts = /* @__PURE__ */ new Map();
8758
- for (const ch of body) counts.set(ch, (counts.get(ch) ?? 0) + 1);
8759
- const distinct = counts.size;
8760
- const maxRun = Math.max(...counts.values());
8761
- if (distinct <= 2 && maxRun / body.length >= 0.8) return true;
7552
+ if (Array.isArray(obj.checks)) return obj.checks.length;
7553
+ if (Array.isArray(obj.signals)) {
7554
+ return obj.signals.reduce((sum, signal) => {
7555
+ const findings = signal.findings;
7556
+ return sum + (Array.isArray(findings) ? findings.length : 0);
7557
+ }, 0);
8762
7558
  }
8763
- return false;
8764
- }
8765
- function isSyntheticFixtureSecretValue(value) {
8766
- return value.includes("abcdefghijklmnopqrstuvwxyz") || value.includes("0123456789abcdefghijklmnopqrstuvwxyz") || value.includes("abcdefghijklmnopqrstuvwxyz0123456789") || value.includes("abcdefghijklmnopqrst");
7559
+ return 0;
8767
7560
  }
8768
- function hasSuspiciousDependencies(repoPath, manifest) {
8769
- if (!manifest.endsWith("package.json")) return false;
8770
- const fullPath = join3(repoPath, manifest);
8771
- if (!isRegularFile(fullPath)) return false;
8772
- const parsed = parseJsonObject(readFileSync6(fullPath, "utf8"));
8773
- if (!parsed) return false;
8774
- const dependencies = isRecord(parsed.dependencies) ? parsed.dependencies : {};
8775
- const devDependencies = isRecord(parsed.devDependencies) ? parsed.devDependencies : {};
8776
- const names = [...Object.keys(dependencies), ...Object.keys(devDependencies)];
8777
- return names.some(
8778
- (name) => /^(todo|fake|placeholder|example)-|does-not-exist| hallucinated/i.test(name)
8779
- );
7561
+ function rawToolName(raw) {
7562
+ const obj = raw;
7563
+ if (Array.isArray(obj.runs)) {
7564
+ const firstRun = obj.runs[0];
7565
+ return firstRun?.tool?.driver?.name ?? "unknown";
7566
+ }
7567
+ if (typeof obj.tool === "string" && obj.tool.length > 0) return obj.tool;
7568
+ return "scorecard";
8780
7569
  }
8781
- function readRecentCommits(repoPath) {
7570
+ function parseIngestFile(filePath) {
7571
+ let raw;
8782
7572
  try {
8783
- const output = execFileSync("git", ["log", "--max-count=12", "--format=%H%x00%s"], {
8784
- cwd: repoPath,
8785
- encoding: "utf8",
8786
- stdio: ["ignore", "pipe", "ignore"]
8787
- }).trim();
8788
- if (!output) return [];
8789
- return output.split("\n").map((line) => {
8790
- const [sha = "", subject = ""] = line.split("\0");
8791
- return { sha, subject };
8792
- }).filter((commit) => commit.sha.length >= 7);
8793
- } catch {
8794
- return [];
7573
+ raw = JSON.parse(stripBom(readFileSync5(filePath, "utf8")));
7574
+ } catch (error) {
7575
+ const message = error instanceof Error ? error.message : String(error);
7576
+ throw new Error(`Cejel: could not parse ingest file as JSON: ${filePath} (${message})`);
8795
7577
  }
7578
+ let signals;
7579
+ if (looksLikeSarif(raw)) signals = parseSarifJson(raw);
7580
+ else if (looksLikeScorecard(raw)) signals = parseScorecardJson(raw);
7581
+ else if (isGenericSignalDocument(raw)) signals = parseGenericJson(raw);
7582
+ if (!signals) {
7583
+ throw new Error(
7584
+ `Cejel: unrecognized ingest file format: ${filePath} \u2014 expected SARIF (a "runs" array), OpenSSF Scorecard JSON (a "checks" array), or the generic Cejel external-signal shape (a "tool" string + "signals" array). See the cejel README "Aggregate your scanners".`
7585
+ );
7586
+ }
7587
+ const rawCount = countRawEntries(raw);
7588
+ const mappedCount = signals.reduce((sum, signal) => sum + signal.findings.length, 0);
7589
+ if (rawCount > 0 && mappedCount === 0) {
7590
+ process.stderr.write(
7591
+ `Cejel: ${rawCount} findings from ${rawToolName(raw)} (${filePath}), 0 mapped to trust criteria
7592
+ `
7593
+ );
7594
+ }
7595
+ return signals.map((signal) => ({
7596
+ ...signal,
7597
+ findings: signal.findings.map(clampFinding)
7598
+ }));
8796
7599
  }
8797
- function readPackageScripts(packageJsonPath) {
8798
- if (!isRegularFile(packageJsonPath)) return /* @__PURE__ */ new Map();
8799
- const parsed = parseJsonObject(readFileSync6(packageJsonPath, "utf8"));
8800
- const scripts = parsed?.scripts;
8801
- if (!isRecord(scripts)) return /* @__PURE__ */ new Map();
8802
- return new Map(
8803
- Object.entries(scripts).filter(
8804
- (entry) => typeof entry[1] === "string"
8805
- )
8806
- );
8807
- }
8808
- function evidenceForRelative(repoPath, path, kind, label) {
8809
- const fullPath = join3(repoPath, path);
8810
- const contents = isRegularFile(fullPath) ? readFileSync6(fullPath, "utf8") : "";
8811
- return {
8812
- kind,
8813
- label,
8814
- path,
8815
- ...contents ? {
8816
- line: firstMeaningfulLine(contents),
8817
- contentHash: createHash("sha256").update(contents).digest("hex")
8818
- } : {}
8819
- };
8820
- }
8821
- function metric(name, label, value, max, weight, unit, description, kind) {
8822
- return {
8823
- name,
8824
- label,
8825
- value: Math.max(0, value),
8826
- max,
8827
- ...kind ? { kind } : {},
8828
- weight,
8829
- unit,
8830
- description
8831
- };
8832
- }
8833
- function firstMeaningfulLine(contents) {
8834
- const lines = contents.split("\n");
8835
- const index = lines.findIndex((line) => line.trim().length > 0);
8836
- return index === -1 ? 1 : index + 1;
8837
- }
8838
- function readGitHead(repoPath) {
7600
+ function expandIngestPattern(pattern) {
7601
+ if (!pattern.includes("*")) return [pattern];
7602
+ const lastSlash = pattern.lastIndexOf("/");
7603
+ const dir = lastSlash === -1 ? "." : pattern.slice(0, lastSlash);
7604
+ const filePattern = lastSlash === -1 ? pattern : pattern.slice(lastSlash + 1);
7605
+ const regexSource = filePattern.replace(/[.+^${}()|[\]\\]/g, "\\$&").replace(/\*/g, ".*");
7606
+ const regex = new RegExp(`^${regexSource}$`);
7607
+ let entries;
8839
7608
  try {
8840
- return execFileSync("git", ["rev-parse", "HEAD"], {
8841
- cwd: repoPath,
8842
- encoding: "utf8",
8843
- stdio: ["ignore", "pipe", "ignore"]
8844
- }).trim();
7609
+ entries = readdirSync2(dir);
8845
7610
  } catch {
8846
- return null;
7611
+ return [];
8847
7612
  }
7613
+ return entries.filter((name) => regex.test(name)).sort().map((name) => join2(dir, name));
8848
7614
  }
8849
- function hasEnvPathInGitHistory(repoPath) {
7615
+ function discoverIngestInputs(repoPath) {
7616
+ const inputsDir = join2(repoPath, ".cejel", "inputs");
7617
+ let entries;
8850
7618
  try {
8851
- const output = execFileSync(
8852
- "git",
8853
- ["log", "--all", "--diff-filter=AM", "--name-only", "--format="],
8854
- {
8855
- cwd: repoPath,
8856
- encoding: "utf8",
8857
- stdio: ["ignore", "pipe", "ignore"],
8858
- maxBuffer: 512e3
8859
- }
8860
- ).trim();
8861
- if (!output) return false;
8862
- return output.split("\n").some((p) => /(?:^|\/)\.env(?:\.|$)/i.test(p.trim()));
7619
+ entries = readdirSync2(inputsDir);
8863
7620
  } catch {
8864
- return false;
7621
+ return [];
8865
7622
  }
7623
+ return entries.filter((name) => /\.(sarif|json)$/i.test(name)).sort().map((name) => join2(inputsDir, name));
8866
7624
  }
8867
7625
 
8868
- // ../witan/src/rubric.ts
7626
+ // src/witan/rubric.ts
8869
7627
  var WITAN_RUBRIC = [
8870
7628
  {
8871
7629
  id: "A1",
@@ -8924,7 +7682,7 @@ var WITAN_RUBRIC = [
8924
7682
  }
8925
7683
  ];
8926
7684
 
8927
- // ../witan/src/scoring.ts
7685
+ // src/witan/scoring.ts
8928
7686
  var MAX_SIGNAL_ADJUSTMENT = 0.8;
8929
7687
  function createWitanReport(input, inputSignals, rubric = WITAN_RUBRIC) {
8930
7688
  const parsedInput = WitanReportInputSchema.parse(input);
@@ -9232,7 +7990,7 @@ function roundScore(score) {
9232
7990
  return Math.round(score * 10) / 10;
9233
7991
  }
9234
7992
 
9235
- // ../witan/src/public-scan.ts
7993
+ // src/witan/public-scan.ts
9236
7994
  function scoreRepoWithPublicCejel(options) {
9237
7995
  const input = buildWitanInputFromRepo({
9238
7996
  productSlug: options.productSlug,
@@ -9268,85 +8026,15 @@ function resolvePublicIngestSignals(options) {
9268
8026
  return files.flatMap((file) => parseIngestFile(file));
9269
8027
  }
9270
8028
 
9271
- // ../witan/src/repo-clone.ts
9272
- import { execFileSync as execFileSync2 } from "child_process";
9273
- import { mkdirSync, rmSync } from "fs";
9274
- import { tmpdir } from "os";
9275
- import { join as join4 } from "path";
9276
-
9277
- // ../witan/src/cejel-package-name.ts
9278
- import { readFileSync as readFileSync7 } from "fs";
9279
- import { fileURLToPath } from "url";
9280
-
9281
- // ../witan/src/leaderboard.ts
9282
- var RESERVED_CORPUS_SLUGS = ["biome", "tsconfig", "package"];
9283
- var LeaderboardCorpusEntrySchema = external_exports.object({
9284
- // Also the evidence-report slug (reports/<name>.{json,md,svg}) — min length 3
9285
- // to satisfy the WitanReport productSlug pattern.
9286
- name: external_exports.string().regex(/^[a-z0-9][a-z0-9-]{1,61}[a-z0-9]$/).refine((value) => !RESERVED_CORPUS_SLUGS.includes(value), {
9287
- message: "Corpus entry name collides with a tool config filename (reports/<name>.json would be discovered by that tool) \u2014 pick a different slug, e.g. biomejs."
9288
- }),
9289
- category: external_exports.string().min(1).max(80),
9290
- expectedArchetype: external_exports.string().min(1).max(40),
9291
- license: external_exports.string().min(1).max(80),
9292
- /**
9293
- * Repository visibility — the redaction policy's first-class input
9294
- * (goal_cejel_redaction_policy_is_verifiability_2026-07-12): a path is
9295
- * published exactly when the reader can check it (public), and withheld
9296
- * entirely when they can't (private). FAIL CLOSED: absent or unrecognized
9297
- * resolves to 'private' via `.catch` rather than throwing or defaulting
9298
- * open, so a corpus entry can never accidentally publish paths by omission.
9299
- */
9300
- visibility: external_exports.enum(["public", "private"]).catch("private"),
9301
- url: external_exports.string().url().optional(),
9302
- /**
9303
- * Immutable source snapshot for URL entries. A rubric rescore always uses
9304
- * the same commits; changing one is a separate corpus update.
9305
- */
9306
- commit: external_exports.string().regex(/^[0-9a-f]{40}$/).optional(),
9307
- self: external_exports.literal(true).optional(),
9308
- /**
9309
- * A directory inside THIS repository (relative to its root), for internal
9310
- * entries that are a sub-package rather than the whole repo (e.g. the public
9311
- * cejel CLI at packages/witan-cli). Scored locally like "self".
9312
- */
9313
- path: external_exports.string().min(1).max(200).regex(/^[A-Za-z0-9._/-]+$/).refine((value) => !value.startsWith("/") && !value.split("/").includes(".."), {
9314
- message: 'Corpus entry "path" must be relative and must not traverse upward.'
9315
- }).optional()
9316
- }).strict().refine((entry) => (entry.url ? 1 : 0) + (entry.self ? 1 : 0) + (entry.path ? 1 : 0) === 1, {
9317
- message: 'Corpus entry must have exactly one of "url", "self", or "path".'
9318
- }).refine((entry) => entry.url ? entry.commit !== void 0 : entry.commit === void 0, {
9319
- message: 'Every URL corpus entry must declare exactly one immutable 40-character "commit".'
9320
- });
9321
- var LeaderboardCorpusSchema = external_exports.object({
9322
- comment: external_exports.string().min(1),
9323
- entries: external_exports.array(LeaderboardCorpusEntrySchema).min(1)
9324
- }).strict().refine(
9325
- (corpus) => new Set(corpus.entries.map((entry) => entry.name)).size === corpus.entries.length,
9326
- { message: "Corpus entry names must be unique." }
9327
- );
9328
-
9329
- // ../witan/src/quant-integrity.ts
9330
- import { readFileSync as readFileSync10 } from "fs";
9331
- import { join as join8 } from "path";
9332
-
9333
- // ../witan/src/quant-metrics-grading.ts
9334
- import { createHash as createHash2 } from "crypto";
9335
- import { readFileSync as readFileSync9 } from "fs";
9336
- import { join as join7 } from "path";
9337
-
9338
- // ../witan/src/quant-run-tier-grading.ts
9339
- import { createHash as createHash3 } from "crypto";
9340
-
9341
8029
  // src/product-identity.ts
9342
- import { existsSync as existsSync3, readFileSync as readFileSync11 } from "fs";
9343
- import { basename as basename3, join as join9 } from "path";
8030
+ import { existsSync, readFileSync as readFileSync6 } from "fs";
8031
+ import { basename as basename2, join as join3 } from "path";
9344
8032
  var SLUG_PATTERN = /^[a-z0-9][a-z0-9-]{1,62}[a-z0-9]$/;
9345
8033
  var FALLBACK_SLUG = "repo";
9346
8034
  var FALLBACK_DISPLAY_NAME = "Repository";
9347
8035
  function deriveProductIdentity(repoPath) {
9348
- const packageJsonPath = join9(repoPath, "package.json");
9349
- const raw = readPackageName(packageJsonPath) ?? basename3(repoPath);
8036
+ const packageJsonPath = join3(repoPath, "package.json");
8037
+ const raw = readPackageName(packageJsonPath) ?? basename2(repoPath);
9350
8038
  const displayName = raw.trim().length > 0 ? raw.trim() : FALLBACK_DISPLAY_NAME;
9351
8039
  return {
9352
8040
  productSlug: slugify(raw),
@@ -9354,9 +8042,9 @@ function deriveProductIdentity(repoPath) {
9354
8042
  };
9355
8043
  }
9356
8044
  function readPackageName(packageJsonPath) {
9357
- if (!existsSync3(packageJsonPath)) return void 0;
8045
+ if (!existsSync(packageJsonPath)) return void 0;
9358
8046
  try {
9359
- const parsed = JSON.parse(readFileSync11(packageJsonPath, "utf8"));
8047
+ const parsed = JSON.parse(readFileSync6(packageJsonPath, "utf8"));
9360
8048
  if (typeof parsed === "object" && parsed !== null && "name" in parsed) {
9361
8049
  const name = parsed.name;
9362
8050
  if (typeof name === "string" && name.trim().length > 0) return name;
@@ -9432,13 +8120,15 @@ export {
9432
8120
  __commonJS,
9433
8121
  __export,
9434
8122
  __toESM,
9435
- formatExternalSourceLine,
9436
- renderWitanHtmlReport,
9437
- renderWitanBadgeEndpoint,
9438
- renderWitanBadgeSvg,
9439
8123
  ZodOptional,
9440
8124
  ZodFirstPartyTypeKind,
9441
8125
  objectType,
9442
8126
  external_exports,
8127
+ formatExternalSourceLine,
8128
+ renderWitanHtmlReport,
8129
+ renderWitanBadgeEndpoint,
8130
+ renderWitanBadgeSvg,
8131
+ serializeWitanReport,
8132
+ createWitanAttestation,
9443
8133
  runCejelScan
9444
8134
  };