@eduardbar/drift 1.2.0 → 1.4.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (195) hide show
  1. package/.gga +50 -0
  2. package/.github/actions/drift-review/README.md +60 -0
  3. package/.github/actions/drift-review/action.yml +131 -0
  4. package/.github/actions/drift-scan/README.md +28 -32
  5. package/.github/actions/drift-scan/action.yml +78 -14
  6. package/.github/workflows/publish-vscode.yml +3 -3
  7. package/.github/workflows/publish.yml +3 -3
  8. package/.github/workflows/review-pr.yml +94 -9
  9. package/AGENTS.md +75 -245
  10. package/CHANGELOG.md +28 -0
  11. package/README.md +308 -51
  12. package/ROADMAP.md +6 -5
  13. package/dist/analyzer.d.ts +2 -2
  14. package/dist/analyzer.js +420 -159
  15. package/dist/benchmark.d.ts +2 -0
  16. package/dist/benchmark.js +204 -0
  17. package/dist/cli.js +693 -67
  18. package/dist/config.js +16 -2
  19. package/dist/diff.js +66 -10
  20. package/dist/doctor.d.ts +5 -0
  21. package/dist/doctor.js +133 -0
  22. package/dist/format.d.ts +17 -0
  23. package/dist/format.js +45 -0
  24. package/dist/git.js +12 -0
  25. package/dist/guard-types.d.ts +57 -0
  26. package/dist/guard-types.js +2 -0
  27. package/dist/guard.d.ts +14 -0
  28. package/dist/guard.js +239 -0
  29. package/dist/index.d.ts +12 -3
  30. package/dist/index.js +6 -1
  31. package/dist/init.d.ts +15 -0
  32. package/dist/init.js +273 -0
  33. package/dist/map-cycles.d.ts +2 -0
  34. package/dist/map-cycles.js +34 -0
  35. package/dist/map-svg.d.ts +19 -0
  36. package/dist/map-svg.js +97 -0
  37. package/dist/map.js +78 -138
  38. package/dist/metrics.js +70 -55
  39. package/dist/output-metadata.d.ts +13 -0
  40. package/dist/output-metadata.js +17 -0
  41. package/dist/plugins-capabilities.d.ts +4 -0
  42. package/dist/plugins-capabilities.js +21 -0
  43. package/dist/plugins-messages.d.ts +10 -0
  44. package/dist/plugins-messages.js +16 -0
  45. package/dist/plugins-rules.d.ts +9 -0
  46. package/dist/plugins-rules.js +137 -0
  47. package/dist/plugins.d.ts +2 -1
  48. package/dist/plugins.js +80 -28
  49. package/dist/printer.js +4 -0
  50. package/dist/reporter-constants.d.ts +16 -0
  51. package/dist/reporter-constants.js +39 -0
  52. package/dist/reporter.d.ts +3 -3
  53. package/dist/reporter.js +35 -55
  54. package/dist/review.d.ts +2 -1
  55. package/dist/review.js +4 -3
  56. package/dist/rules/comments.js +2 -2
  57. package/dist/rules/complexity.js +2 -7
  58. package/dist/rules/nesting.js +3 -13
  59. package/dist/rules/phase0-basic.js +10 -10
  60. package/dist/rules/phase3-configurable.js +23 -15
  61. package/dist/rules/shared.d.ts +2 -0
  62. package/dist/rules/shared.js +27 -3
  63. package/dist/saas/constants.d.ts +15 -0
  64. package/dist/saas/constants.js +48 -0
  65. package/dist/saas/dashboard.d.ts +8 -0
  66. package/dist/saas/dashboard.js +132 -0
  67. package/dist/saas/errors.d.ts +19 -0
  68. package/dist/saas/errors.js +37 -0
  69. package/dist/saas/helpers.d.ts +21 -0
  70. package/dist/saas/helpers.js +110 -0
  71. package/dist/saas/ingest.d.ts +3 -0
  72. package/dist/saas/ingest.js +249 -0
  73. package/dist/saas/organization.d.ts +5 -0
  74. package/dist/saas/organization.js +82 -0
  75. package/dist/saas/plan-change.d.ts +10 -0
  76. package/dist/saas/plan-change.js +15 -0
  77. package/dist/saas/store.d.ts +21 -0
  78. package/dist/saas/store.js +159 -0
  79. package/dist/saas/types.d.ts +191 -0
  80. package/dist/saas/types.js +2 -0
  81. package/dist/saas.d.ts +8 -82
  82. package/dist/saas.js +7 -320
  83. package/dist/sarif.d.ts +74 -0
  84. package/dist/sarif.js +122 -0
  85. package/dist/trust-advanced.d.ts +14 -0
  86. package/dist/trust-advanced.js +65 -0
  87. package/dist/trust-kpi-fs.d.ts +3 -0
  88. package/dist/trust-kpi-fs.js +141 -0
  89. package/dist/trust-kpi-parse.d.ts +7 -0
  90. package/dist/trust-kpi-parse.js +186 -0
  91. package/dist/trust-kpi-types.d.ts +16 -0
  92. package/dist/trust-kpi-types.js +2 -0
  93. package/dist/trust-kpi.d.ts +7 -0
  94. package/dist/trust-kpi.js +185 -0
  95. package/dist/trust-policy.d.ts +32 -0
  96. package/dist/trust-policy.js +160 -0
  97. package/dist/trust-render.d.ts +9 -0
  98. package/dist/trust-render.js +54 -0
  99. package/dist/trust-scoring.d.ts +9 -0
  100. package/dist/trust-scoring.js +208 -0
  101. package/dist/trust.d.ts +37 -0
  102. package/dist/trust.js +168 -0
  103. package/dist/types/app.d.ts +30 -0
  104. package/dist/types/app.js +2 -0
  105. package/dist/types/config.d.ts +25 -0
  106. package/dist/types/config.js +2 -0
  107. package/dist/types/core.d.ts +100 -0
  108. package/dist/types/core.js +2 -0
  109. package/dist/types/diff.d.ts +55 -0
  110. package/dist/types/diff.js +2 -0
  111. package/dist/types/plugin.d.ts +41 -0
  112. package/dist/types/plugin.js +2 -0
  113. package/dist/types/trust.d.ts +120 -0
  114. package/dist/types/trust.js +2 -0
  115. package/dist/types.d.ts +8 -211
  116. package/docs/PRD.md +187 -109
  117. package/docs/plugin-contract.md +61 -0
  118. package/docs/release-notes-draft.md +40 -0
  119. package/docs/rules-catalog.md +49 -0
  120. package/docs/trust-core-release-checklist.md +87 -0
  121. package/package.json +6 -3
  122. package/packages/vscode-drift/src/code-actions.ts +1 -1
  123. package/schemas/drift-ai-output.v1.json +162 -0
  124. package/schemas/drift-report.v1.json +151 -0
  125. package/schemas/drift-trust.v1.json +131 -0
  126. package/scripts/smoke-repo.mjs +394 -0
  127. package/src/analyzer.ts +484 -155
  128. package/src/benchmark.ts +266 -0
  129. package/src/cli.ts +840 -85
  130. package/src/config.ts +19 -2
  131. package/src/diff.ts +84 -10
  132. package/src/doctor.ts +173 -0
  133. package/src/format.ts +81 -0
  134. package/src/git.ts +16 -0
  135. package/src/guard-types.ts +64 -0
  136. package/src/guard.ts +324 -0
  137. package/src/index.ts +83 -0
  138. package/src/init.ts +298 -0
  139. package/src/map-cycles.ts +38 -0
  140. package/src/map-svg.ts +124 -0
  141. package/src/map.ts +111 -142
  142. package/src/metrics.ts +78 -59
  143. package/src/output-metadata.ts +30 -0
  144. package/src/plugins-capabilities.ts +36 -0
  145. package/src/plugins-messages.ts +35 -0
  146. package/src/plugins-rules.ts +296 -0
  147. package/src/plugins.ts +148 -27
  148. package/src/printer.ts +4 -0
  149. package/src/reporter-constants.ts +46 -0
  150. package/src/reporter.ts +64 -65
  151. package/src/review.ts +6 -4
  152. package/src/rules/comments.ts +2 -2
  153. package/src/rules/complexity.ts +2 -7
  154. package/src/rules/nesting.ts +3 -13
  155. package/src/rules/phase0-basic.ts +11 -12
  156. package/src/rules/phase3-configurable.ts +39 -26
  157. package/src/rules/shared.ts +31 -3
  158. package/src/saas/constants.ts +56 -0
  159. package/src/saas/dashboard.ts +172 -0
  160. package/src/saas/errors.ts +45 -0
  161. package/src/saas/helpers.ts +140 -0
  162. package/src/saas/ingest.ts +278 -0
  163. package/src/saas/organization.ts +99 -0
  164. package/src/saas/plan-change.ts +19 -0
  165. package/src/saas/store.ts +172 -0
  166. package/src/saas/types.ts +216 -0
  167. package/src/saas.ts +49 -433
  168. package/src/sarif.ts +232 -0
  169. package/src/trust-advanced.ts +99 -0
  170. package/src/trust-kpi-fs.ts +169 -0
  171. package/src/trust-kpi-parse.ts +219 -0
  172. package/src/trust-kpi-types.ts +19 -0
  173. package/src/trust-kpi.ts +210 -0
  174. package/src/trust-policy.ts +246 -0
  175. package/src/trust-render.ts +61 -0
  176. package/src/trust-scoring.ts +231 -0
  177. package/src/trust.ts +260 -0
  178. package/src/types/app.ts +30 -0
  179. package/src/types/config.ts +27 -0
  180. package/src/types/core.ts +105 -0
  181. package/src/types/diff.ts +61 -0
  182. package/src/types/plugin.ts +46 -0
  183. package/src/types/trust.ts +134 -0
  184. package/src/types.ts +78 -238
  185. package/tests/cli-sarif.test.ts +92 -0
  186. package/tests/diff.test.ts +124 -0
  187. package/tests/format.test.ts +157 -0
  188. package/tests/new-features.test.ts +80 -1
  189. package/tests/phase1-init-doctor-guard.test.ts +199 -0
  190. package/tests/plugins.test.ts +219 -0
  191. package/tests/rules.test.ts +23 -1
  192. package/tests/saas-foundation.test.ts +358 -1
  193. package/tests/sarif.test.ts +160 -0
  194. package/tests/trust-kpi.test.ts +147 -0
  195. package/tests/trust.test.ts +602 -0
package/src/guard.ts ADDED
@@ -0,0 +1,324 @@
1
+ import { existsSync, readFileSync } from 'node:fs'
2
+ import { relative, resolve } from 'node:path'
3
+ import { analyzeProject } from './analyzer.js'
4
+ import { loadConfig } from './config.js'
5
+ import { computeDiff } from './diff.js'
6
+ import { cleanupTempDir, extractFilesAtRef } from './git.js'
7
+ import { buildReport } from './reporter.js'
8
+ import type { DriftDiff, DriftReport } from './types.js'
9
+ import type {
10
+ GuardBaseline,
11
+ GuardCheck,
12
+ GuardEvaluation,
13
+ GuardMetrics,
14
+ GuardOptions,
15
+ GuardResult,
16
+ GuardThresholds,
17
+ IssueSeverity,
18
+ } from './guard-types.js'
19
+
20
+ interface NormalizedBaseline {
21
+ score?: number
22
+ totalIssues?: number
23
+ bySeverity: Partial<Record<IssueSeverity, number>>
24
+ }
25
+
26
+ interface GuardEvalInput {
27
+ metrics: GuardMetrics
28
+ budget?: number
29
+ bySeverity?: GuardThresholds
30
+ enforceNoRegression: {
31
+ score: boolean
32
+ totalIssues: boolean
33
+ }
34
+ }
35
+
36
+ interface GuardRuntimeState {
37
+ currentReport: DriftReport
38
+ config: Awaited<ReturnType<typeof loadConfig>>
39
+ projectPath: string
40
+ }
41
+
42
+ interface DiffGuardResultInput {
43
+ projectPath: string
44
+ currentReport: DriftReport
45
+ options: GuardOptions
46
+ tempDir: string
47
+ config: Awaited<ReturnType<typeof loadConfig>>
48
+ baseRef: string
49
+ }
50
+
51
+ interface BaselineGuardResultInput {
52
+ projectPath: string
53
+ currentReport: DriftReport
54
+ options: GuardOptions
55
+ baseline: NormalizedBaseline
56
+ baselinePath?: string
57
+ }
58
+
59
+ function parseNumber(value: unknown): number | undefined {
60
+ return typeof value === 'number' && !Number.isNaN(value) ? value : undefined
61
+ }
62
+
63
+ function normalizeBaseline(baseline: GuardBaseline): NormalizedBaseline {
64
+ const bySeverityFromRoot = baseline.bySeverity
65
+ const bySeverity = {
66
+ error: parseNumber(bySeverityFromRoot?.error) ?? parseNumber(baseline.errors) ?? parseNumber(baseline.summary?.errors),
67
+ warning: parseNumber(bySeverityFromRoot?.warning) ?? parseNumber(baseline.warnings) ?? parseNumber(baseline.summary?.warnings),
68
+ info: parseNumber(bySeverityFromRoot?.info) ?? parseNumber(baseline.infos) ?? parseNumber(baseline.summary?.infos),
69
+ }
70
+
71
+ const normalized: NormalizedBaseline = {
72
+ score: parseNumber(baseline.score),
73
+ totalIssues: parseNumber(baseline.totalIssues),
74
+ bySeverity,
75
+ }
76
+
77
+ const hasAnyAnchor =
78
+ normalized.score !== undefined ||
79
+ normalized.totalIssues !== undefined ||
80
+ normalized.bySeverity.error !== undefined ||
81
+ normalized.bySeverity.warning !== undefined ||
82
+ normalized.bySeverity.info !== undefined
83
+
84
+ if (!hasAnyAnchor) {
85
+ throw new Error('Invalid guard baseline: expected score, totalIssues, or severity counters (error/warning/info).')
86
+ }
87
+
88
+ return normalized
89
+ }
90
+
91
+ function readBaselineFromFile(projectPath: string, baselinePath?: string): { baseline: NormalizedBaseline; path: string } | undefined {
92
+ const resolvedBaselinePath = resolve(projectPath, baselinePath ?? 'drift-baseline.json')
93
+ if (!existsSync(resolvedBaselinePath)) return undefined
94
+
95
+ const raw = JSON.parse(readFileSync(resolvedBaselinePath, 'utf8')) as GuardBaseline
96
+ return {
97
+ baseline: normalizeBaseline(raw),
98
+ path: resolvedBaselinePath,
99
+ }
100
+ }
101
+
102
+ function remapBaseReportPaths(baseReport: DriftReport, tempDir: string, projectPath: string): DriftReport {
103
+ return {
104
+ ...baseReport,
105
+ files: baseReport.files.map((file) => ({
106
+ ...file,
107
+ path: resolve(projectPath, relative(tempDir, file.path)),
108
+ })),
109
+ }
110
+ }
111
+
112
+ function countSeverityDeltaFromDiff(diff: DriftDiff): Record<IssueSeverity, number> {
113
+ const severityDelta: Record<IssueSeverity, number> = {
114
+ error: 0,
115
+ warning: 0,
116
+ info: 0,
117
+ }
118
+
119
+ for (const file of diff.files) {
120
+ for (const issue of file.newIssues) {
121
+ severityDelta[issue.severity] += 1
122
+ }
123
+ for (const issue of file.resolvedIssues) {
124
+ severityDelta[issue.severity] -= 1
125
+ }
126
+ }
127
+
128
+ return severityDelta
129
+ }
130
+
131
+ function buildMetricsFromDiff(diff: DriftDiff): GuardMetrics {
132
+ return {
133
+ scoreDelta: diff.totalDelta,
134
+ totalIssuesDelta: diff.newIssuesCount - diff.resolvedIssuesCount,
135
+ severityDelta: countSeverityDeltaFromDiff(diff),
136
+ }
137
+ }
138
+
139
+ function buildMetricsFromBaseline(current: DriftReport, baseline: NormalizedBaseline): GuardMetrics {
140
+ return {
141
+ scoreDelta: current.totalScore - (baseline.score ?? current.totalScore),
142
+ totalIssuesDelta: current.totalIssues - (baseline.totalIssues ?? current.totalIssues),
143
+ severityDelta: {
144
+ error: current.summary.errors - (baseline.bySeverity.error ?? current.summary.errors),
145
+ warning: current.summary.warnings - (baseline.bySeverity.warning ?? current.summary.warnings),
146
+ info: current.summary.infos - (baseline.bySeverity.info ?? current.summary.infos),
147
+ },
148
+ }
149
+ }
150
+
151
+ interface GuardCheckInput {
152
+ id: string
153
+ actual: number
154
+ limit: number
155
+ message: string
156
+ }
157
+
158
+ function addCheck(checks: GuardCheck[], input: GuardCheckInput): void {
159
+ checks.push({
160
+ id: input.id,
161
+ passed: input.actual <= input.limit,
162
+ actual: input.actual,
163
+ limit: input.limit,
164
+ message: input.message,
165
+ })
166
+ }
167
+
168
+ export function evaluateGuard(input: GuardEvalInput): GuardEvaluation {
169
+ const checks: GuardCheck[] = []
170
+
171
+ if (input.enforceNoRegression.score) {
172
+ addCheck(checks, {
173
+ id: 'no-regression-score',
174
+ actual: input.metrics.scoreDelta,
175
+ limit: 0,
176
+ message: 'Score delta must be <= 0.',
177
+ })
178
+ }
179
+
180
+ if (input.enforceNoRegression.totalIssues) {
181
+ addCheck(checks, {
182
+ id: 'no-regression-total-issues',
183
+ actual: input.metrics.totalIssuesDelta,
184
+ limit: 0,
185
+ message: 'Total issues delta must be <= 0.',
186
+ })
187
+ }
188
+
189
+ if (typeof input.budget === 'number' && !Number.isNaN(input.budget)) {
190
+ addCheck(checks, {
191
+ id: 'budget-total-delta',
192
+ actual: input.metrics.scoreDelta,
193
+ limit: input.budget,
194
+ message: `Score delta must be <= budget (${input.budget}).`,
195
+ })
196
+ }
197
+
198
+ const severityThresholds = input.bySeverity
199
+ if (severityThresholds) {
200
+ const severities: IssueSeverity[] = ['error', 'warning', 'info']
201
+ for (const severity of severities) {
202
+ const threshold = severityThresholds[severity]
203
+ if (typeof threshold !== 'number' || Number.isNaN(threshold)) continue
204
+ addCheck(checks, {
205
+ id: `severity-${severity}`,
206
+ actual: input.metrics.severityDelta[severity],
207
+ limit: threshold,
208
+ message: `${severity} delta must be <= ${threshold}.`,
209
+ })
210
+ }
211
+ }
212
+
213
+ return {
214
+ passed: checks.every((check) => check.passed),
215
+ checks,
216
+ }
217
+ }
218
+
219
+ export async function runGuard(targetPath: string, options: GuardOptions = {}): Promise<GuardResult> {
220
+ const runtimeState = await initializeGuardRuntime(targetPath, options)
221
+ const { projectPath, config, currentReport } = runtimeState
222
+
223
+ let tempDir: string | undefined
224
+ try {
225
+ if (options.baseRef) {
226
+ tempDir = extractFilesAtRef(projectPath, options.baseRef)
227
+ return createDiffGuardResult({
228
+ projectPath,
229
+ currentReport,
230
+ options,
231
+ tempDir,
232
+ config,
233
+ baseRef: options.baseRef,
234
+ })
235
+ }
236
+
237
+ const inlineBaseline = options.baseline ? normalizeBaseline(options.baseline) : undefined
238
+ const fileBaseline = inlineBaseline ? undefined : readBaselineFromFile(projectPath, options.baselinePath)
239
+ const baseline = inlineBaseline ?? fileBaseline?.baseline
240
+ const baselinePath = fileBaseline?.path
241
+
242
+ if (!baseline) {
243
+ throw new Error('Guard requires a comparison point: provide baseRef or a baseline (inline or file).')
244
+ }
245
+
246
+ return createBaselineGuardResult({
247
+ projectPath,
248
+ currentReport,
249
+ options,
250
+ baseline,
251
+ baselinePath,
252
+ })
253
+ } finally {
254
+ if (tempDir) cleanupTempDir(tempDir)
255
+ }
256
+ }
257
+
258
+ async function initializeGuardRuntime(targetPath: string, options: GuardOptions): Promise<GuardRuntimeState> {
259
+ const projectPath = resolve(targetPath)
260
+ const config = await loadConfig(projectPath)
261
+ const currentFiles = analyzeProject(projectPath, config, options.analysis)
262
+ const currentReport = buildReport(projectPath, currentFiles)
263
+
264
+ return {
265
+ projectPath,
266
+ config,
267
+ currentReport,
268
+ }
269
+ }
270
+
271
+ function createDiffGuardResult(input: DiffGuardResultInput): GuardResult {
272
+ const { projectPath, currentReport, options, tempDir, config, baseRef } = input
273
+ const baseFiles = analyzeProject(tempDir, config, options.analysis)
274
+ const baseReport = buildReport(tempDir, baseFiles)
275
+ const remappedBase = remapBaseReportPaths(baseReport, tempDir, projectPath)
276
+ const diff = computeDiff(remappedBase, currentReport, baseRef)
277
+ const metrics = buildMetricsFromDiff(diff)
278
+ const evaluation = evaluateGuard({
279
+ metrics,
280
+ budget: options.budget,
281
+ bySeverity: options.bySeverity,
282
+ enforceNoRegression: {
283
+ score: true,
284
+ totalIssues: true,
285
+ },
286
+ })
287
+
288
+ return {
289
+ scannedAt: new Date().toISOString(),
290
+ projectPath,
291
+ mode: 'diff',
292
+ passed: evaluation.passed,
293
+ baseRef,
294
+ metrics,
295
+ checks: evaluation.checks,
296
+ current: currentReport,
297
+ diff,
298
+ }
299
+ }
300
+
301
+ function createBaselineGuardResult(input: BaselineGuardResultInput): GuardResult {
302
+ const { projectPath, currentReport, options, baseline, baselinePath } = input
303
+ const metrics = buildMetricsFromBaseline(currentReport, baseline)
304
+ const evaluation = evaluateGuard({
305
+ metrics,
306
+ budget: options.budget,
307
+ bySeverity: options.bySeverity,
308
+ enforceNoRegression: {
309
+ score: baseline.score !== undefined,
310
+ totalIssues: baseline.totalIssues !== undefined,
311
+ },
312
+ })
313
+
314
+ return {
315
+ scannedAt: new Date().toISOString(),
316
+ projectPath,
317
+ mode: 'baseline',
318
+ passed: evaluation.passed,
319
+ baselinePath,
320
+ metrics,
321
+ checks: evaluation.checks,
322
+ current: currentReport,
323
+ }
324
+ }
package/src/index.ts CHANGED
@@ -1,7 +1,51 @@
1
1
  export { analyzeProject, analyzeFile, RULE_WEIGHTS } from './analyzer.js'
2
2
  export { buildReport, formatMarkdown } from './reporter.js'
3
3
  export { computeDiff } from './diff.js'
4
+ export { runGuard, evaluateGuard } from './guard.js'
5
+ export type {
6
+ GuardBaseline,
7
+ GuardThresholds,
8
+ GuardOptions,
9
+ GuardMetrics,
10
+ GuardCheck,
11
+ GuardEvaluation,
12
+ GuardResult,
13
+ } from './guard-types.js'
4
14
  export { generateReview, formatReviewMarkdown } from './review.js'
15
+ export { runDoctor } from './doctor.js'
16
+ export type { DoctorOptions } from './doctor.js'
17
+ export {
18
+ buildTrustReport,
19
+ formatTrustConsole,
20
+ formatTrustMarkdown,
21
+ formatTrustJson,
22
+ resolveTrustGatePolicy,
23
+ evaluateTrustGate,
24
+ shouldFailByMaxRisk,
25
+ shouldFailTrustGate,
26
+ normalizeMergeRiskLevel,
27
+ MERGE_RISK_ORDER,
28
+ } from './trust.js'
29
+ export type {
30
+ TrustGateOptions,
31
+ TrustGatePolicyResolutionOptions,
32
+ TrustGatePolicyResolutionStep,
33
+ TrustGateEvaluation,
34
+ } from './trust.js'
35
+ export {
36
+ computeTrustKpis,
37
+ computeTrustKpisFromReports,
38
+ formatTrustKpiConsole,
39
+ formatTrustKpiJson,
40
+ } from './trust-kpi.js'
41
+ export { toSarif, diffToSarif } from './sarif.js'
42
+ export type {
43
+ SarifLevel,
44
+ DriftSarifRule,
45
+ DriftSarifResult,
46
+ DriftSarifRun,
47
+ DriftSarifLog,
48
+ } from './sarif.js'
5
49
  export { generateArchitectureMap, generateArchitectureSvg } from './map.js'
6
50
  export type {
7
51
  DriftReport,
@@ -12,8 +56,19 @@ export type {
12
56
  DriftConfig,
13
57
  RepoQualityScore,
14
58
  MaintenanceRiskMetrics,
59
+ DriftTrustReport,
60
+ TrustReason,
61
+ TrustFixPriority,
62
+ TrustDiffContext,
63
+ TrustKpiReport,
64
+ TrustKpiDiagnostic,
65
+ TrustDiffTrendSummary,
66
+ TrustScoreStats,
67
+ MergeRiskLevel,
15
68
  DriftPlugin,
16
69
  DriftPluginRule,
70
+ TrustGatePolicyConfig,
71
+ TrustAdvancedContext,
17
72
  } from './types.js'
18
73
  export { loadHistory, saveSnapshot } from './snapshot.js'
19
74
  export type { SnapshotEntry, SnapshotHistory } from './snapshot.js'
@@ -21,14 +76,42 @@ export {
21
76
  DEFAULT_SAAS_POLICY,
22
77
  defaultSaasStorePath,
23
78
  resolveSaasPolicy,
79
+ SaasActorRequiredError,
80
+ SaasPermissionError,
81
+ getRequiredRoleForOperation,
82
+ assertSaasPermission,
83
+ getSaasEffectiveLimits,
84
+ getOrganizationEffectiveLimits,
85
+ changeOrganizationPlan,
86
+ listOrganizationPlanChanges,
87
+ getOrganizationUsageSnapshot,
24
88
  ingestSnapshotFromReport,
89
+ listSaasSnapshots,
25
90
  getSaasSummary,
26
91
  generateSaasDashboardHtml,
27
92
  } from './saas.js'
28
93
  export type {
94
+ SaasUser,
95
+ SaasOrganization,
96
+ SaasWorkspace,
97
+ SaasRepo,
98
+ SaasMembership,
99
+ SaasRole,
100
+ SaasPlan,
29
101
  SaasPolicy,
102
+ SaasPolicyOverrides,
30
103
  SaasStore,
31
104
  SaasSummary,
32
105
  SaasSnapshot,
106
+ SaasQueryOptions,
33
107
  IngestOptions,
108
+ SaasPlanChange,
109
+ SaasOperation,
110
+ SaasPermissionContext,
111
+ SaasPermissionResult,
112
+ SaasEffectiveLimits,
113
+ SaasOrganizationUsageSnapshot,
114
+ ChangeOrganizationPlanOptions,
115
+ SaasUsageQueryOptions,
116
+ SaasPlanChangeQueryOptions,
34
117
  } from './saas.js'