@yasserkhanorg/e2e-agents 0.5.15 → 0.6.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 (105) hide show
  1. package/dist/agent/pipeline.d.ts +1 -1
  2. package/dist/agent/pipeline.d.ts.map +1 -1
  3. package/dist/agent/plan.d.ts +0 -12
  4. package/dist/agent/plan.d.ts.map +1 -1
  5. package/dist/agent/plan.js +0 -365
  6. package/dist/agent/types.d.ts +42 -0
  7. package/dist/agent/types.d.ts.map +1 -0
  8. package/dist/agent/types.js +4 -0
  9. package/dist/api.d.ts +10 -14
  10. package/dist/api.d.ts.map +1 -1
  11. package/dist/api.js +29 -59
  12. package/dist/cli.js +41 -174
  13. package/dist/engine/impact_engine.d.ts +36 -0
  14. package/dist/engine/impact_engine.d.ts.map +1 -0
  15. package/dist/engine/impact_engine.js +196 -0
  16. package/dist/engine/plan_builder.d.ts +9 -0
  17. package/dist/engine/plan_builder.d.ts.map +1 -0
  18. package/dist/engine/plan_builder.js +329 -0
  19. package/dist/esm/agent/plan.js +1 -360
  20. package/dist/esm/agent/types.js +3 -0
  21. package/dist/esm/api.js +27 -56
  22. package/dist/esm/cli.js +40 -173
  23. package/dist/esm/engine/impact_engine.js +191 -0
  24. package/dist/esm/engine/plan_builder.js +323 -0
  25. package/dist/esm/index.js +6 -3
  26. package/dist/esm/knowledge/route_families.js +57 -0
  27. package/dist/index.d.ts +9 -4
  28. package/dist/index.d.ts.map +1 -1
  29. package/dist/index.js +14 -5
  30. package/dist/knowledge/route_families.d.ts +19 -0
  31. package/dist/knowledge/route_families.d.ts.map +1 -1
  32. package/dist/knowledge/route_families.js +60 -0
  33. package/package.json +1 -1
  34. package/dist/agent/ai_flow_analysis.d.ts +0 -13
  35. package/dist/agent/ai_flow_analysis.d.ts.map +0 -1
  36. package/dist/agent/ai_flow_analysis.js +0 -334
  37. package/dist/agent/ai_mapping.d.ts +0 -14
  38. package/dist/agent/ai_mapping.d.ts.map +0 -1
  39. package/dist/agent/ai_mapping.js +0 -559
  40. package/dist/agent/analysis.d.ts +0 -64
  41. package/dist/agent/analysis.d.ts.map +0 -1
  42. package/dist/agent/analysis.js +0 -292
  43. package/dist/agent/blast_radius.d.ts +0 -4
  44. package/dist/agent/blast_radius.d.ts.map +0 -1
  45. package/dist/agent/blast_radius.js +0 -37
  46. package/dist/agent/dependency_graph.d.ts +0 -14
  47. package/dist/agent/dependency_graph.d.ts.map +0 -1
  48. package/dist/agent/dependency_graph.js +0 -227
  49. package/dist/agent/flags.d.ts +0 -23
  50. package/dist/agent/flags.d.ts.map +0 -1
  51. package/dist/agent/flags.js +0 -171
  52. package/dist/agent/flow_catalog.d.ts +0 -25
  53. package/dist/agent/flow_catalog.d.ts.map +0 -1
  54. package/dist/agent/flow_catalog.js +0 -115
  55. package/dist/agent/flow_mapping.d.ts +0 -10
  56. package/dist/agent/flow_mapping.d.ts.map +0 -1
  57. package/dist/agent/flow_mapping.js +0 -84
  58. package/dist/agent/framework.d.ts +0 -13
  59. package/dist/agent/framework.d.ts.map +0 -1
  60. package/dist/agent/framework.js +0 -149
  61. package/dist/agent/gap_suggestions.d.ts +0 -14
  62. package/dist/agent/gap_suggestions.d.ts.map +0 -1
  63. package/dist/agent/gap_suggestions.js +0 -101
  64. package/dist/agent/generator.d.ts +0 -10
  65. package/dist/agent/generator.d.ts.map +0 -1
  66. package/dist/agent/generator.js +0 -115
  67. package/dist/agent/operational_insights.d.ts +0 -41
  68. package/dist/agent/operational_insights.d.ts.map +0 -1
  69. package/dist/agent/operational_insights.js +0 -127
  70. package/dist/agent/report.d.ts +0 -97
  71. package/dist/agent/report.d.ts.map +0 -1
  72. package/dist/agent/report.js +0 -159
  73. package/dist/agent/runner.d.ts +0 -7
  74. package/dist/agent/runner.d.ts.map +0 -1
  75. package/dist/agent/runner.js +0 -898
  76. package/dist/agent/selectors.d.ts +0 -10
  77. package/dist/agent/selectors.d.ts.map +0 -1
  78. package/dist/agent/selectors.js +0 -75
  79. package/dist/agent/subsystem_risk.d.ts +0 -23
  80. package/dist/agent/subsystem_risk.d.ts.map +0 -1
  81. package/dist/agent/subsystem_risk.js +0 -207
  82. package/dist/agent/tests.d.ts +0 -19
  83. package/dist/agent/tests.d.ts.map +0 -1
  84. package/dist/agent/tests.js +0 -116
  85. package/dist/agent/traceability.d.ts +0 -22
  86. package/dist/agent/traceability.d.ts.map +0 -1
  87. package/dist/agent/traceability.js +0 -183
  88. package/dist/esm/agent/ai_flow_analysis.js +0 -331
  89. package/dist/esm/agent/ai_mapping.js +0 -556
  90. package/dist/esm/agent/analysis.js +0 -287
  91. package/dist/esm/agent/blast_radius.js +0 -34
  92. package/dist/esm/agent/dependency_graph.js +0 -224
  93. package/dist/esm/agent/flags.js +0 -160
  94. package/dist/esm/agent/flow_catalog.js +0 -112
  95. package/dist/esm/agent/flow_mapping.js +0 -81
  96. package/dist/esm/agent/framework.js +0 -145
  97. package/dist/esm/agent/gap_suggestions.js +0 -98
  98. package/dist/esm/agent/generator.js +0 -112
  99. package/dist/esm/agent/operational_insights.js +0 -124
  100. package/dist/esm/agent/report.js +0 -156
  101. package/dist/esm/agent/runner.js +0 -894
  102. package/dist/esm/agent/selectors.js +0 -71
  103. package/dist/esm/agent/subsystem_risk.js +0 -204
  104. package/dist/esm/agent/tests.js +0 -111
  105. package/dist/esm/agent/traceability.js +0 -180
@@ -0,0 +1,323 @@
1
+ // Copyright (c) 2015-present Mattermost, Inc. All Rights Reserved.
2
+ // See LICENSE.txt for license information.
3
+ import { mkdirSync, writeFileSync } from 'fs';
4
+ import { dirname, join } from 'path';
5
+ import { minimatch } from 'minimatch';
6
+ import { getGaps, getPartialGaps } from './impact_engine.js';
7
+ const DEFAULT_POLICY = {
8
+ minConfidenceForTargeted: 60,
9
+ safeMergeMinConfidence: 85,
10
+ forceFullOnWarningsAtOrAbove: 2,
11
+ forceFullOnP0WithGaps: true,
12
+ forceFullOnRiskyFiles: true,
13
+ riskyFilePatterns: [
14
+ '**/auth/**',
15
+ '**/login/**',
16
+ '**/permissions/**',
17
+ '**/admin/**',
18
+ '**/security/**',
19
+ '**/migrations/**',
20
+ '**/schema/**',
21
+ '**/*.sql',
22
+ '**/webhook/**',
23
+ ],
24
+ enforcementMode: 'advisory',
25
+ blockOnActions: ['must-add-tests'],
26
+ };
27
+ function featureLabel(f) {
28
+ return f.featureId || f.familyId;
29
+ }
30
+ function computeConfidence(impact) {
31
+ const gaps = getGaps(impact);
32
+ const totalFeatures = impact.impactedFeatures.length;
33
+ const boundRatio = totalFeatures > 0
34
+ ? (totalFeatures / (totalFeatures + impact.unboundFiles.length))
35
+ : 1;
36
+ // Graph-resolved bindings start at 100
37
+ let confidence = 100;
38
+ // Deduct for unbound files (not mapped to any family)
39
+ if (impact.unboundFiles.length > 0) {
40
+ const unboundPenalty = Math.min(30, impact.unboundFiles.length * 3);
41
+ confidence -= unboundPenalty;
42
+ }
43
+ // Deduct for gaps
44
+ confidence -= Math.min(20, gaps.length * 5);
45
+ // Deduct for warnings
46
+ confidence -= Math.min(15, impact.warnings.length * 5);
47
+ // Bonus for high bound ratio
48
+ if (boundRatio >= 0.9) {
49
+ confidence = Math.min(100, confidence + 5);
50
+ }
51
+ return Math.max(0, Math.min(100, confidence));
52
+ }
53
+ function findRiskyFiles(changedFiles, patterns) {
54
+ return [...new Set(changedFiles.filter((file) => patterns.some((pattern) => minimatch(file, pattern, { matchBase: true }))))];
55
+ }
56
+ function pickRunSet(impact, confidence, policy) {
57
+ const gaps = getGaps(impact);
58
+ const reasons = [];
59
+ const triggeredRules = [];
60
+ const riskyFiles = findRiskyFiles(impact.changedFiles, policy.riskyFilePatterns);
61
+ const hasP0 = impact.impactedFeatures.some((f) => f.priority === 'P0');
62
+ if (gaps.length > 0) {
63
+ reasons.push(`${gaps.length} uncovered P0/P1 feature(s) detected.`);
64
+ }
65
+ if (hasP0) {
66
+ reasons.push('P0 features are impacted by this change set.');
67
+ }
68
+ if (policy.forceFullOnRiskyFiles && riskyFiles.length > 0) {
69
+ triggeredRules.push('risky-files');
70
+ reasons.push(`Risky file patterns matched: ${riskyFiles.join(', ')}`);
71
+ }
72
+ if (confidence < policy.minConfidenceForTargeted) {
73
+ triggeredRules.push('low-confidence');
74
+ }
75
+ if (impact.warnings.length >= policy.forceFullOnWarningsAtOrAbove) {
76
+ triggeredRules.push('warning-threshold');
77
+ reasons.push('Warning threshold exceeded.');
78
+ }
79
+ if (policy.forceFullOnP0WithGaps && hasP0 && gaps.length > 0) {
80
+ triggeredRules.push('p0-with-gaps');
81
+ }
82
+ if (triggeredRules.length > 0) {
83
+ return {
84
+ runSet: 'full',
85
+ reasons: reasons.length > 0 ? reasons : ['Policy rules triggered full suite.'],
86
+ triggeredRules,
87
+ riskyFiles,
88
+ };
89
+ }
90
+ // If we have impacted features with specs, recommend targeted
91
+ const coveredFeatures = impact.impactedFeatures.filter((f) => f.coverageStatus !== 'uncovered');
92
+ if (coveredFeatures.length > 0) {
93
+ return {
94
+ runSet: 'targeted',
95
+ reasons: reasons.length > 0 ? reasons : ['Impacted features have test coverage.'],
96
+ triggeredRules,
97
+ riskyFiles,
98
+ };
99
+ }
100
+ return {
101
+ runSet: 'smoke',
102
+ reasons: reasons.length > 0 ? reasons : ['No targeted tests mapped from impacted features.'],
103
+ triggeredRules,
104
+ riskyFiles,
105
+ };
106
+ }
107
+ function buildDecision(impact, runSet, confidence, policy) {
108
+ const gaps = getGaps(impact);
109
+ if (gaps.length > 0) {
110
+ return {
111
+ action: 'must-add-tests',
112
+ title: 'Must add tests',
113
+ summary: `Detected ${gaps.length} uncovered P0/P1 feature(s). Add or update tests before merge.`,
114
+ };
115
+ }
116
+ if (impact.changedFiles.length === 0 && impact.impactedFeatures.length === 0) {
117
+ return {
118
+ action: 'safe-to-merge',
119
+ title: 'Safe to merge',
120
+ summary: 'No app file changes detected — no E2E coverage required for this change set.',
121
+ };
122
+ }
123
+ if (runSet === 'smoke' && confidence >= policy.safeMergeMinConfidence && impact.warnings.length === 0) {
124
+ return {
125
+ action: 'safe-to-merge',
126
+ title: 'Safe to merge',
127
+ summary: 'No critical coverage gaps were detected and confidence is high.',
128
+ };
129
+ }
130
+ const coveredCount = impact.impactedFeatures.filter((f) => f.coverageStatus !== 'uncovered').length;
131
+ const coveredSuffix = coveredCount > 0
132
+ ? ` All ${coveredCount} impacted feature(s) have test coverage.`
133
+ : '';
134
+ return {
135
+ action: 'run-now',
136
+ title: 'Run now',
137
+ summary: `Impacted features are covered by existing tests.${coveredSuffix} Verify with the E2E suite before merge.`,
138
+ };
139
+ }
140
+ function evaluateEnforcement(decision, policy) {
141
+ const blockOnActions = (policy.blockOnActions && policy.blockOnActions.length > 0)
142
+ ? [...policy.blockOnActions]
143
+ : ['must-add-tests'];
144
+ const matchedAction = blockOnActions.includes(decision.action);
145
+ if (policy.enforcementMode === 'block' && matchedAction) {
146
+ return {
147
+ mode: policy.enforcementMode,
148
+ blockOnActions,
149
+ matchedAction,
150
+ shouldFail: true,
151
+ summary: `Blocking mode active: decision "${decision.action}" is configured to fail CI.`,
152
+ };
153
+ }
154
+ if (policy.enforcementMode === 'warn' && matchedAction) {
155
+ return {
156
+ mode: policy.enforcementMode,
157
+ blockOnActions,
158
+ matchedAction,
159
+ shouldFail: false,
160
+ summary: `Warning mode active: decision "${decision.action}" is advisory-only for CI.`,
161
+ };
162
+ }
163
+ if (policy.enforcementMode === 'block') {
164
+ return {
165
+ mode: policy.enforcementMode,
166
+ blockOnActions,
167
+ matchedAction,
168
+ shouldFail: false,
169
+ summary: `Blocking mode active, but decision "${decision.action}" is not configured for CI failure.`,
170
+ };
171
+ }
172
+ return {
173
+ mode: policy.enforcementMode,
174
+ blockOnActions,
175
+ matchedAction,
176
+ shouldFail: false,
177
+ summary: 'Advisory mode active: recommendations do not fail CI by default.',
178
+ };
179
+ }
180
+ /**
181
+ * Build recommended test list from impacted features' Playwright specs.
182
+ */
183
+ function buildRecommendedTests(impact) {
184
+ const tests = [];
185
+ for (const feature of impact.impactedFeatures) {
186
+ if (feature.coverageStatus !== 'uncovered') {
187
+ for (const spec of feature.playwrightSpecs) {
188
+ if (!tests.includes(spec)) {
189
+ tests.push(spec);
190
+ }
191
+ }
192
+ }
193
+ }
194
+ return tests;
195
+ }
196
+ export function buildPlanFromImpact(impact, policyOverride) {
197
+ const policy = { ...DEFAULT_POLICY, ...(policyOverride || {}) };
198
+ const confidence = computeConfidence(impact);
199
+ const runSetResult = pickRunSet(impact, confidence, policy);
200
+ const decision = buildDecision(impact, runSetResult.runSet, confidence, policy);
201
+ const enforcement = evaluateEnforcement(decision, policy);
202
+ const gaps = getGaps(impact);
203
+ const partialGaps = getPartialGaps(impact);
204
+ const gapDetails = gaps.map((f) => ({
205
+ id: featureLabel(f),
206
+ name: featureLabel(f),
207
+ priority: f.priority,
208
+ reasons: [`No Playwright or Cypress tests found for ${featureLabel(f)}`],
209
+ files: f.changedFiles.slice(0, 6),
210
+ missingScenarios: f.userFlows.length > 0 ? f.userFlows.slice(0, 5) : undefined,
211
+ }));
212
+ // Add partial gaps as advisory info
213
+ for (const f of partialGaps) {
214
+ const source = f.playwrightSpecs.length > 0 ? 'Cypress' : 'Playwright';
215
+ gapDetails.push({
216
+ id: featureLabel(f),
217
+ name: `${featureLabel(f)} (partial)`,
218
+ priority: f.priority,
219
+ reasons: [`Missing ${source} tests for ${featureLabel(f)} (has ${f.playwrightSpecs.length > 0 ? 'Playwright' : 'Cypress'} only)`],
220
+ files: f.changedFiles.slice(0, 6),
221
+ });
222
+ }
223
+ const coveredFlows = impact.impactedFeatures
224
+ .filter((f) => f.coverageStatus === 'covered')
225
+ .map((f) => ({
226
+ id: featureLabel(f),
227
+ name: featureLabel(f),
228
+ priority: f.priority,
229
+ coveredBy: [
230
+ ...(f.playwrightSpecs.length > 0 ? [`${f.playwrightSpecs.length} Playwright spec(s)`] : []),
231
+ ...(f.cypressSpecs.length > 0 ? [`${f.cypressSpecs.length} Cypress spec(s)`] : []),
232
+ ].slice(0, 3),
233
+ }));
234
+ const recommendedTests = buildRecommendedTests(impact);
235
+ const requiredNewTests = gaps.map((f) => `${featureLabel(f)}: Add E2E tests`);
236
+ const p0 = impact.impactedFeatures.filter((f) => f.priority === 'P0').length;
237
+ const p1 = impact.impactedFeatures.filter((f) => f.priority === 'P1').length;
238
+ const p2 = impact.impactedFeatures.filter((f) => f.priority === 'P2').length;
239
+ const runId = `plan-${Date.now().toString(36)}`;
240
+ return {
241
+ schemaVersion: '1.0.0',
242
+ runId,
243
+ generatedAt: new Date().toISOString(),
244
+ source: 'impact',
245
+ runSet: runSetResult.runSet,
246
+ confidence,
247
+ reasons: runSetResult.reasons,
248
+ recommendedTests,
249
+ requiredNewTests,
250
+ gapDetails,
251
+ coveredFlows,
252
+ policy: {
253
+ riskyFiles: runSetResult.riskyFiles,
254
+ triggeredRules: runSetResult.triggeredRules,
255
+ applied: policy,
256
+ },
257
+ decision,
258
+ enforcement,
259
+ metrics: {
260
+ changedFiles: impact.changedFiles.length,
261
+ impactedFlows: impact.impactedFeatures.length,
262
+ p0Flows: p0,
263
+ p1Flows: p1,
264
+ p2Flows: p2,
265
+ uncoveredP0P1Flows: gaps.length,
266
+ warnings: impact.warnings.length,
267
+ },
268
+ };
269
+ }
270
+ export function writePlanReport(appRoot, plan) {
271
+ const baseDir = join(appRoot, '.e2e-ai-agents');
272
+ mkdirSync(baseDir, { recursive: true });
273
+ const planPath = join(baseDir, 'plan.json');
274
+ writeFileSync(planPath, JSON.stringify(plan, null, 2), 'utf-8');
275
+ return planPath;
276
+ }
277
+ export function renderCiSummaryMarkdown(plan) {
278
+ const lines = [];
279
+ const { p0Flows, p1Flows, uncoveredP0P1Flows, changedFiles, impactedFlows } = plan.metrics;
280
+ const mustAddTests = plan.decision.action === 'must-add-tests';
281
+ const statusEmoji = mustAddTests ? '🔴' : plan.decision.action === 'safe-to-merge' ? '🟢' : '🟡';
282
+ lines.push(`## ${statusEmoji} E2E Coverage: ${plan.decision.title}`);
283
+ lines.push('');
284
+ lines.push(`${plan.decision.summary}`);
285
+ lines.push('');
286
+ lines.push(`**${changedFiles}** files changed → **${impactedFlows}** features impacted` +
287
+ (p0Flows > 0 || p1Flows > 0 ? ` (P0: ${p0Flows}, P1: ${p1Flows})` : ''));
288
+ if (mustAddTests && plan.requiredNewTests.length > 0) {
289
+ lines.push('');
290
+ lines.push('### ⚠️ Add E2E tests for these uncovered P0/P1 features');
291
+ lines.push('');
292
+ lines.push(`The following ${uncoveredP0P1Flows} feature(s) have no test coverage and must be covered before merge:`);
293
+ lines.push('');
294
+ for (const gap of plan.gapDetails.filter((g) => !g.name.includes('(partial)'))) {
295
+ lines.push(`- **${gap.name}** [${gap.priority}]`);
296
+ if (gap.missingScenarios && gap.missingScenarios.length > 0) {
297
+ for (const scenario of gap.missingScenarios) {
298
+ lines.push(` - ${scenario}`);
299
+ }
300
+ }
301
+ }
302
+ }
303
+ if (plan.coveredFlows.length > 0) {
304
+ lines.push('');
305
+ lines.push('### ✅ Covered features');
306
+ lines.push('');
307
+ for (const flow of plan.coveredFlows) {
308
+ lines.push(`- **${flow.name}** [${flow.priority}] — ${flow.coveredBy.join(', ')}`);
309
+ }
310
+ }
311
+ if (plan.confidence < 100) {
312
+ lines.push('');
313
+ lines.push(`**Confidence**: ${plan.confidence}%`);
314
+ }
315
+ return lines.join('\n');
316
+ }
317
+ export function writeCiSummary(appRoot, markdown, relativePath = '.e2e-ai-agents/ci-summary.md') {
318
+ const fullPath = join(appRoot, relativePath);
319
+ const dir = dirname(fullPath);
320
+ mkdirSync(dir, { recursive: true });
321
+ writeFileSync(fullPath, markdown, 'utf-8');
322
+ return fullPath;
323
+ }
package/dist/esm/index.js CHANGED
@@ -8,8 +8,11 @@ export { OpenAIProvider, checkOpenAISetup } from './openai_provider.js';
8
8
  export { CustomProvider } from './custom_provider.js';
9
9
  // Factory
10
10
  export { LLMProviderFactory, validateProviderSetup } from './provider_factory.js';
11
- // Agent API (impact, gap, suggest, traceability ingest)
12
- export { analyzeImpact, findGaps, recommendTests, handoffGeneratedTests, ingestTraceability, captureTraceability } from './api.js';
11
+ // Agent API (deterministic impact + plan, traceability)
12
+ export { analyzeImpactDeterministic, recommendTestsDeterministic, handoffGeneratedTests, ingestTraceability, captureTraceability } from './api.js';
13
+ // V2 Engine (deterministic impact + plan)
14
+ export { analyzeImpact as analyzeImpactV2, getGaps, getPartialGaps } from './engine/impact_engine.js';
15
+ export { buildPlanFromImpact } from './engine/plan_builder.js';
13
16
  export { appendFeedbackAndRecompute, readCalibration } from './agent/feedback.js';
14
17
  export { finalizeGeneratedTests } from './agent/handoff.js';
15
18
  export { ingestTraceabilityInput } from './agent/traceability_ingest.js';
@@ -21,6 +24,6 @@ export { buildGenerationPrompt, parseGenerationResponse, detectHallucinatedMetho
21
24
  export { runHealStage, healFromReport, resolveHealTargets, renderHealMarkdown } from './pipeline/stage4_heal.js';
22
25
  export { buildHealPrompt, buildQualityFixPrompt } from './prompts/heal.js';
23
26
  // Knowledge modules
24
- export { loadRouteFamilyManifest, bindFilesToFamilies } from './knowledge/route_families.js';
27
+ export { loadRouteFamilyManifest, bindFilesToFamilies, getCypressSpecDirsForBinding, getPriorityForBinding, getUserFlowsForBinding } from './knowledge/route_families.js';
25
28
  export { buildApiSurface, loadOrBuildApiSurface } from './knowledge/api_surface.js';
26
29
  export { buildSpecIndex, getSpecsForFamily } from './knowledge/spec_index.js';
@@ -63,9 +63,18 @@ function validateFamily(family) {
63
63
  if (Array.isArray(obj.specDirs)) {
64
64
  result.specDirs = obj.specDirs.filter((v) => typeof v === 'string');
65
65
  }
66
+ if (Array.isArray(obj.cypressSpecDirs)) {
67
+ result.cypressSpecDirs = obj.cypressSpecDirs.filter((v) => typeof v === 'string');
68
+ }
66
69
  if (Array.isArray(obj.tags)) {
67
70
  result.tags = obj.tags.filter((v) => typeof v === 'string');
68
71
  }
72
+ if (obj.priority === 'P0' || obj.priority === 'P1' || obj.priority === 'P2') {
73
+ result.priority = obj.priority;
74
+ }
75
+ if (Array.isArray(obj.userFlows)) {
76
+ result.userFlows = obj.userFlows.filter((v) => typeof v === 'string');
77
+ }
69
78
  if (Array.isArray(obj.features)) {
70
79
  result.features = obj.features
71
80
  .map((f) => validateFeature(f))
@@ -94,9 +103,18 @@ function validateFeature(feature) {
94
103
  if (Array.isArray(obj.specDirs)) {
95
104
  result.specDirs = obj.specDirs.filter((v) => typeof v === 'string');
96
105
  }
106
+ if (Array.isArray(obj.cypressSpecDirs)) {
107
+ result.cypressSpecDirs = obj.cypressSpecDirs.filter((v) => typeof v === 'string');
108
+ }
97
109
  if (Array.isArray(obj.tags)) {
98
110
  result.tags = obj.tags.filter((v) => typeof v === 'string');
99
111
  }
112
+ if (obj.priority === 'P0' || obj.priority === 'P1' || obj.priority === 'P2') {
113
+ result.priority = obj.priority;
114
+ }
115
+ if (Array.isArray(obj.userFlows)) {
116
+ result.userFlows = obj.userFlows.filter((v) => typeof v === 'string');
117
+ }
100
118
  return result;
101
119
  }
102
120
  export function loadRouteFamilyManifest(testsRoot, config) {
@@ -193,6 +211,45 @@ export function getSpecDirsForBinding(manifest, binding) {
193
211
  }
194
212
  return family.specDirs || [];
195
213
  }
214
+ export function getCypressSpecDirsForBinding(manifest, binding) {
215
+ const family = getFamilyById(manifest, binding.family);
216
+ if (!family) {
217
+ return [];
218
+ }
219
+ if (binding.feature) {
220
+ const feature = getFeatureById(family, binding.feature);
221
+ if (feature?.cypressSpecDirs && feature.cypressSpecDirs.length > 0) {
222
+ return feature.cypressSpecDirs;
223
+ }
224
+ }
225
+ return family.cypressSpecDirs || [];
226
+ }
227
+ export function getPriorityForBinding(manifest, binding) {
228
+ const family = getFamilyById(manifest, binding.family);
229
+ if (!family) {
230
+ return 'P2';
231
+ }
232
+ if (binding.feature) {
233
+ const feature = getFeatureById(family, binding.feature);
234
+ if (feature?.priority) {
235
+ return feature.priority;
236
+ }
237
+ }
238
+ return family.priority || 'P2';
239
+ }
240
+ export function getUserFlowsForBinding(manifest, binding) {
241
+ const family = getFamilyById(manifest, binding.family);
242
+ if (!family) {
243
+ return [];
244
+ }
245
+ if (binding.feature) {
246
+ const feature = getFeatureById(family, binding.feature);
247
+ if (feature?.userFlows && feature.userFlows.length > 0) {
248
+ return feature.userFlows;
249
+ }
250
+ }
251
+ return family.userFlows || [];
252
+ }
196
253
  export function getRoutesForBinding(manifest, binding) {
197
254
  const family = getFamilyById(manifest, binding.family);
198
255
  if (!family) {
package/dist/index.d.ts CHANGED
@@ -18,8 +18,11 @@ export { OpenAIProvider, checkOpenAISetup } from './openai_provider.js';
18
18
  export { CustomProvider } from './custom_provider.js';
19
19
  export { LLMProviderFactory, validateProviderSetup } from './provider_factory.js';
20
20
  export type { HybridConfig } from './provider_factory.js';
21
- export { analyzeImpact, findGaps, recommendTests, handoffGeneratedTests, ingestTraceability, captureTraceability } from './api.js';
22
- export type { AgentApiOptions, AnalyzeResult, RecommendTestsResult, TraceabilityIngestApiOptions, TraceabilityCaptureApiOptions, } from './api.js';
21
+ export { analyzeImpactDeterministic, recommendTestsDeterministic, handoffGeneratedTests, ingestTraceability, captureTraceability } from './api.js';
22
+ export type { AgentApiOptions, RecommendTestsV2Result, TraceabilityIngestApiOptions, TraceabilityCaptureApiOptions, } from './api.js';
23
+ export { analyzeImpact as analyzeImpactV2, getGaps, getPartialGaps } from './engine/impact_engine.js';
24
+ export type { ImpactResult, ImpactedFeature, CoverageStatus, ImpactEngineOptions } from './engine/impact_engine.js';
25
+ export { buildPlanFromImpact } from './engine/plan_builder.js';
23
26
  export { appendFeedbackAndRecompute, readCalibration } from './agent/feedback.js';
24
27
  export type { RecommendationFeedbackEntry, CalibrationSummary } from './agent/feedback.js';
25
28
  export { finalizeGeneratedTests } from './agent/handoff.js';
@@ -39,10 +42,12 @@ export { runHealStage, healFromReport, resolveHealTargets, renderHealMarkdown }
39
42
  export type { HealConfig, HealTarget, HealResult } from './pipeline/stage4_heal.js';
40
43
  export { buildHealPrompt, buildQualityFixPrompt } from './prompts/heal.js';
41
44
  export type { HealPromptContext } from './prompts/heal.js';
42
- export { loadRouteFamilyManifest, bindFilesToFamilies } from './knowledge/route_families.js';
43
- export type { RouteFamily, RouteFeature, RouteFamilyManifest, FileBinding } from './knowledge/route_families.js';
45
+ export { loadRouteFamilyManifest, bindFilesToFamilies, getCypressSpecDirsForBinding, getPriorityForBinding, getUserFlowsForBinding } from './knowledge/route_families.js';
46
+ export type { RouteFamily, RouteFeature, RouteFamilyManifest, FileBinding, FeaturePriority } from './knowledge/route_families.js';
44
47
  export { buildApiSurface, loadOrBuildApiSurface } from './knowledge/api_surface.js';
45
48
  export type { ApiSurfaceCatalog, PageObjectSurface } from './knowledge/api_surface.js';
46
49
  export { buildSpecIndex, getSpecsForFamily } from './knowledge/spec_index.js';
47
50
  export type { SpecIndex, SpecEntry } from './knowledge/spec_index.js';
51
+ export type { FlowImpact, FlowPriority, FlowCoverage, FlagHit, BlastRadius } from './agent/types.js';
52
+ export type { PlanReport } from './agent/plan.js';
48
53
  //# sourceMappingURL=index.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"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"}
package/dist/index.js CHANGED
@@ -2,7 +2,7 @@
2
2
  // Copyright (c) 2015-present Mattermost, Inc. All Rights Reserved.
3
3
  // See LICENSE.txt for license information.
4
4
  Object.defineProperty(exports, "__esModule", { value: true });
5
- exports.getSpecsForFamily = exports.buildSpecIndex = exports.loadOrBuildApiSurface = exports.buildApiSurface = exports.bindFilesToFamilies = exports.loadRouteFamilyManifest = exports.buildQualityFixPrompt = exports.buildHealPrompt = exports.renderHealMarkdown = exports.resolveHealTargets = exports.healFromReport = exports.runHealStage = exports.detectHallucinatedMethods = exports.parseGenerationResponse = exports.buildGenerationPrompt = exports.runGenerationStage = exports.runPipeline = exports.captureTraceabilityInput = exports.ingestTraceabilityInput = exports.finalizeGeneratedTests = exports.readCalibration = exports.appendFeedbackAndRecompute = exports.captureTraceability = exports.ingestTraceability = exports.handoffGeneratedTests = exports.recommendTests = exports.findGaps = exports.analyzeImpact = exports.validateProviderSetup = exports.LLMProviderFactory = exports.CustomProvider = exports.checkOpenAISetup = exports.OpenAIProvider = exports.checkOllamaSetup = exports.OllamaProvider = exports.checkAnthropicSetup = exports.AnthropicProvider = exports.UnsupportedCapabilityError = exports.LLMProviderError = void 0;
5
+ exports.getSpecsForFamily = exports.buildSpecIndex = exports.loadOrBuildApiSurface = exports.buildApiSurface = exports.getUserFlowsForBinding = exports.getPriorityForBinding = exports.getCypressSpecDirsForBinding = exports.bindFilesToFamilies = exports.loadRouteFamilyManifest = exports.buildQualityFixPrompt = exports.buildHealPrompt = exports.renderHealMarkdown = exports.resolveHealTargets = exports.healFromReport = exports.runHealStage = exports.detectHallucinatedMethods = exports.parseGenerationResponse = exports.buildGenerationPrompt = exports.runGenerationStage = exports.runPipeline = exports.captureTraceabilityInput = exports.ingestTraceabilityInput = exports.finalizeGeneratedTests = exports.readCalibration = exports.appendFeedbackAndRecompute = exports.buildPlanFromImpact = exports.getPartialGaps = exports.getGaps = exports.analyzeImpactV2 = exports.captureTraceability = exports.ingestTraceability = exports.handoffGeneratedTests = exports.recommendTestsDeterministic = exports.analyzeImpactDeterministic = exports.validateProviderSetup = exports.LLMProviderFactory = exports.CustomProvider = exports.checkOpenAISetup = exports.OpenAIProvider = exports.checkOllamaSetup = exports.OllamaProvider = exports.checkAnthropicSetup = exports.AnthropicProvider = exports.UnsupportedCapabilityError = exports.LLMProviderError = void 0;
6
6
  var provider_interface_js_1 = require("./provider_interface.js");
7
7
  Object.defineProperty(exports, "LLMProviderError", { enumerable: true, get: function () { return provider_interface_js_1.LLMProviderError; } });
8
8
  Object.defineProperty(exports, "UnsupportedCapabilityError", { enumerable: true, get: function () { return provider_interface_js_1.UnsupportedCapabilityError; } });
@@ -22,14 +22,20 @@ Object.defineProperty(exports, "CustomProvider", { enumerable: true, get: functi
22
22
  var provider_factory_js_1 = require("./provider_factory.js");
23
23
  Object.defineProperty(exports, "LLMProviderFactory", { enumerable: true, get: function () { return provider_factory_js_1.LLMProviderFactory; } });
24
24
  Object.defineProperty(exports, "validateProviderSetup", { enumerable: true, get: function () { return provider_factory_js_1.validateProviderSetup; } });
25
- // Agent API (impact, gap, suggest, traceability ingest)
25
+ // Agent API (deterministic impact + plan, traceability)
26
26
  var api_js_1 = require("./api.js");
27
- Object.defineProperty(exports, "analyzeImpact", { enumerable: true, get: function () { return api_js_1.analyzeImpact; } });
28
- Object.defineProperty(exports, "findGaps", { enumerable: true, get: function () { return api_js_1.findGaps; } });
29
- Object.defineProperty(exports, "recommendTests", { enumerable: true, get: function () { return api_js_1.recommendTests; } });
27
+ Object.defineProperty(exports, "analyzeImpactDeterministic", { enumerable: true, get: function () { return api_js_1.analyzeImpactDeterministic; } });
28
+ Object.defineProperty(exports, "recommendTestsDeterministic", { enumerable: true, get: function () { return api_js_1.recommendTestsDeterministic; } });
30
29
  Object.defineProperty(exports, "handoffGeneratedTests", { enumerable: true, get: function () { return api_js_1.handoffGeneratedTests; } });
31
30
  Object.defineProperty(exports, "ingestTraceability", { enumerable: true, get: function () { return api_js_1.ingestTraceability; } });
32
31
  Object.defineProperty(exports, "captureTraceability", { enumerable: true, get: function () { return api_js_1.captureTraceability; } });
32
+ // V2 Engine (deterministic impact + plan)
33
+ var impact_engine_js_1 = require("./engine/impact_engine.js");
34
+ Object.defineProperty(exports, "analyzeImpactV2", { enumerable: true, get: function () { return impact_engine_js_1.analyzeImpact; } });
35
+ Object.defineProperty(exports, "getGaps", { enumerable: true, get: function () { return impact_engine_js_1.getGaps; } });
36
+ Object.defineProperty(exports, "getPartialGaps", { enumerable: true, get: function () { return impact_engine_js_1.getPartialGaps; } });
37
+ var plan_builder_js_1 = require("./engine/plan_builder.js");
38
+ Object.defineProperty(exports, "buildPlanFromImpact", { enumerable: true, get: function () { return plan_builder_js_1.buildPlanFromImpact; } });
33
39
  var feedback_js_1 = require("./agent/feedback.js");
34
40
  Object.defineProperty(exports, "appendFeedbackAndRecompute", { enumerable: true, get: function () { return feedback_js_1.appendFeedbackAndRecompute; } });
35
41
  Object.defineProperty(exports, "readCalibration", { enumerable: true, get: function () { return feedback_js_1.readCalibration; } });
@@ -60,6 +66,9 @@ Object.defineProperty(exports, "buildQualityFixPrompt", { enumerable: true, get:
60
66
  var route_families_js_1 = require("./knowledge/route_families.js");
61
67
  Object.defineProperty(exports, "loadRouteFamilyManifest", { enumerable: true, get: function () { return route_families_js_1.loadRouteFamilyManifest; } });
62
68
  Object.defineProperty(exports, "bindFilesToFamilies", { enumerable: true, get: function () { return route_families_js_1.bindFilesToFamilies; } });
69
+ Object.defineProperty(exports, "getCypressSpecDirsForBinding", { enumerable: true, get: function () { return route_families_js_1.getCypressSpecDirsForBinding; } });
70
+ Object.defineProperty(exports, "getPriorityForBinding", { enumerable: true, get: function () { return route_families_js_1.getPriorityForBinding; } });
71
+ Object.defineProperty(exports, "getUserFlowsForBinding", { enumerable: true, get: function () { return route_families_js_1.getUserFlowsForBinding; } });
63
72
  var api_surface_js_1 = require("./knowledge/api_surface.js");
64
73
  Object.defineProperty(exports, "buildApiSurface", { enumerable: true, get: function () { return api_surface_js_1.buildApiSurface; } });
65
74
  Object.defineProperty(exports, "loadOrBuildApiSurface", { enumerable: true, get: function () { return api_surface_js_1.loadOrBuildApiSurface; } });
@@ -1,10 +1,14 @@
1
+ export type FeaturePriority = 'P0' | 'P1' | 'P2';
1
2
  export interface RouteFeature {
2
3
  id: string;
3
4
  routes?: string[];
4
5
  webappPaths?: string[];
5
6
  serverPaths?: string[];
6
7
  specDirs?: string[];
8
+ cypressSpecDirs?: string[];
7
9
  tags?: string[];
10
+ priority?: FeaturePriority;
11
+ userFlows?: string[];
8
12
  }
9
13
  export interface RouteFamily {
10
14
  id: string;
@@ -14,7 +18,10 @@ export interface RouteFamily {
14
18
  webappPaths?: string[];
15
19
  serverPaths?: string[];
16
20
  specDirs?: string[];
21
+ cypressSpecDirs?: string[];
17
22
  tags?: string[];
23
+ priority?: FeaturePriority;
24
+ userFlows?: string[];
18
25
  features?: RouteFeature[];
19
26
  }
20
27
  export interface RouteFamilyManifest {
@@ -40,6 +47,18 @@ export declare function getSpecDirsForBinding(manifest: RouteFamilyManifest, bin
40
47
  family: string;
41
48
  feature?: string;
42
49
  }): string[];
50
+ export declare function getCypressSpecDirsForBinding(manifest: RouteFamilyManifest, binding: {
51
+ family: string;
52
+ feature?: string;
53
+ }): string[];
54
+ export declare function getPriorityForBinding(manifest: RouteFamilyManifest, binding: {
55
+ family: string;
56
+ feature?: string;
57
+ }): FeaturePriority;
58
+ export declare function getUserFlowsForBinding(manifest: RouteFamilyManifest, binding: {
59
+ family: string;
60
+ feature?: string;
61
+ }): string[];
43
62
  export declare function getRoutesForBinding(manifest: RouteFamilyManifest, binding: {
44
63
  family: string;
45
64
  feature?: string;
@@ -1 +1 @@
1
- {"version":3,"file":"route_families.d.ts","sourceRoot":"","sources":["../../src/knowledge/route_families.ts"],"names":[],"mappings":"AAMA,MAAM,WAAW,YAAY;IACzB,EAAE,EAAE,MAAM,CAAC;IACX,MAAM,CAAC,EAAE,MAAM,EAAE,CAAC;IAClB,WAAW,CAAC,EAAE,MAAM,EAAE,CAAC;IACvB,WAAW,CAAC,EAAE,MAAM,EAAE,CAAC;IACvB,QAAQ,CAAC,EAAE,MAAM,EAAE,CAAC;IACpB,IAAI,CAAC,EAAE,MAAM,EAAE,CAAC;CACnB;AAED,MAAM,WAAW,WAAW;IACxB,EAAE,EAAE,MAAM,CAAC;IACX,MAAM,EAAE,MAAM,EAAE,CAAC;IACjB,WAAW,CAAC,EAAE,MAAM,EAAE,CAAC;IACvB,UAAU,CAAC,EAAE,MAAM,EAAE,CAAC;IACtB,WAAW,CAAC,EAAE,MAAM,EAAE,CAAC;IACvB,WAAW,CAAC,EAAE,MAAM,EAAE,CAAC;IACvB,QAAQ,CAAC,EAAE,MAAM,EAAE,CAAC;IACpB,IAAI,CAAC,EAAE,MAAM,EAAE,CAAC;IAChB,QAAQ,CAAC,EAAE,YAAY,EAAE,CAAC;CAC7B;AAED,MAAM,WAAW,mBAAmB;IAChC,QAAQ,EAAE,WAAW,EAAE,CAAC;IACxB,MAAM,EAAE,MAAM,CAAC;CAClB;AAED,MAAM,WAAW,WAAW;IACxB,IAAI,EAAE,MAAM,CAAC;IACb,QAAQ,EAAE,KAAK,CAAC;QAAC,MAAM,EAAE,MAAM,CAAC;QAAC,OAAO,CAAC,EAAE,MAAM,CAAA;KAAC,CAAC,CAAC;CACvD;AAED,MAAM,WAAW,iBAAiB;IAC9B,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,MAAM,CAAC,EAAE,OAAO,CAAC;CACpB;AA6GD,wBAAgB,uBAAuB,CAAC,SAAS,EAAE,MAAM,EAAE,MAAM,CAAC,EAAE,iBAAiB,GAAG,mBAAmB,GAAG,IAAI,CAyCjH;AAED,wBAAgB,mBAAmB,CAAC,YAAY,EAAE,MAAM,EAAE,EAAE,QAAQ,EAAE,mBAAmB,GAAG,WAAW,EAAE,CAsCxG;AAED,wBAAgB,aAAa,CAAC,QAAQ,EAAE,mBAAmB,EAAE,QAAQ,EAAE,MAAM,GAAG,WAAW,GAAG,SAAS,CAEtG;AAED,wBAAgB,cAAc,CAAC,MAAM,EAAE,WAAW,EAAE,SAAS,EAAE,MAAM,GAAG,YAAY,GAAG,SAAS,CAE/F;AAED,wBAAgB,qBAAqB,CACjC,QAAQ,EAAE,mBAAmB,EAC7B,OAAO,EAAE;IAAC,MAAM,EAAE,MAAM,CAAC;IAAC,OAAO,CAAC,EAAE,MAAM,CAAA;CAAC,GAC5C,MAAM,EAAE,CAYV;AAED,wBAAgB,mBAAmB,CAC/B,QAAQ,EAAE,mBAAmB,EAC7B,OAAO,EAAE;IAAC,MAAM,EAAE,MAAM,CAAC;IAAC,OAAO,CAAC,EAAE,MAAM,CAAA;CAAC,GAC5C,MAAM,EAAE,CAYV;AAED,wBAAgB,kBAAkB,IAAI,IAAI,CAEzC"}
1
+ {"version":3,"file":"route_families.d.ts","sourceRoot":"","sources":["../../src/knowledge/route_families.ts"],"names":[],"mappings":"AAMA,MAAM,MAAM,eAAe,GAAG,IAAI,GAAG,IAAI,GAAG,IAAI,CAAC;AAEjD,MAAM,WAAW,YAAY;IACzB,EAAE,EAAE,MAAM,CAAC;IACX,MAAM,CAAC,EAAE,MAAM,EAAE,CAAC;IAClB,WAAW,CAAC,EAAE,MAAM,EAAE,CAAC;IACvB,WAAW,CAAC,EAAE,MAAM,EAAE,CAAC;IACvB,QAAQ,CAAC,EAAE,MAAM,EAAE,CAAC;IACpB,eAAe,CAAC,EAAE,MAAM,EAAE,CAAC;IAC3B,IAAI,CAAC,EAAE,MAAM,EAAE,CAAC;IAChB,QAAQ,CAAC,EAAE,eAAe,CAAC;IAC3B,SAAS,CAAC,EAAE,MAAM,EAAE,CAAC;CACxB;AAED,MAAM,WAAW,WAAW;IACxB,EAAE,EAAE,MAAM,CAAC;IACX,MAAM,EAAE,MAAM,EAAE,CAAC;IACjB,WAAW,CAAC,EAAE,MAAM,EAAE,CAAC;IACvB,UAAU,CAAC,EAAE,MAAM,EAAE,CAAC;IACtB,WAAW,CAAC,EAAE,MAAM,EAAE,CAAC;IACvB,WAAW,CAAC,EAAE,MAAM,EAAE,CAAC;IACvB,QAAQ,CAAC,EAAE,MAAM,EAAE,CAAC;IACpB,eAAe,CAAC,EAAE,MAAM,EAAE,CAAC;IAC3B,IAAI,CAAC,EAAE,MAAM,EAAE,CAAC;IAChB,QAAQ,CAAC,EAAE,eAAe,CAAC;IAC3B,SAAS,CAAC,EAAE,MAAM,EAAE,CAAC;IACrB,QAAQ,CAAC,EAAE,YAAY,EAAE,CAAC;CAC7B;AAED,MAAM,WAAW,mBAAmB;IAChC,QAAQ,EAAE,WAAW,EAAE,CAAC;IACxB,MAAM,EAAE,MAAM,CAAC;CAClB;AAED,MAAM,WAAW,WAAW;IACxB,IAAI,EAAE,MAAM,CAAC;IACb,QAAQ,EAAE,KAAK,CAAC;QAAC,MAAM,EAAE,MAAM,CAAC;QAAC,OAAO,CAAC,EAAE,MAAM,CAAA;KAAC,CAAC,CAAC;CACvD;AAED,MAAM,WAAW,iBAAiB;IAC9B,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,MAAM,CAAC,EAAE,OAAO,CAAC;CACpB;AA+HD,wBAAgB,uBAAuB,CAAC,SAAS,EAAE,MAAM,EAAE,MAAM,CAAC,EAAE,iBAAiB,GAAG,mBAAmB,GAAG,IAAI,CAyCjH;AAED,wBAAgB,mBAAmB,CAAC,YAAY,EAAE,MAAM,EAAE,EAAE,QAAQ,EAAE,mBAAmB,GAAG,WAAW,EAAE,CAsCxG;AAED,wBAAgB,aAAa,CAAC,QAAQ,EAAE,mBAAmB,EAAE,QAAQ,EAAE,MAAM,GAAG,WAAW,GAAG,SAAS,CAEtG;AAED,wBAAgB,cAAc,CAAC,MAAM,EAAE,WAAW,EAAE,SAAS,EAAE,MAAM,GAAG,YAAY,GAAG,SAAS,CAE/F;AAED,wBAAgB,qBAAqB,CACjC,QAAQ,EAAE,mBAAmB,EAC7B,OAAO,EAAE;IAAC,MAAM,EAAE,MAAM,CAAC;IAAC,OAAO,CAAC,EAAE,MAAM,CAAA;CAAC,GAC5C,MAAM,EAAE,CAYV;AAED,wBAAgB,4BAA4B,CACxC,QAAQ,EAAE,mBAAmB,EAC7B,OAAO,EAAE;IAAC,MAAM,EAAE,MAAM,CAAC;IAAC,OAAO,CAAC,EAAE,MAAM,CAAA;CAAC,GAC5C,MAAM,EAAE,CAYV;AAED,wBAAgB,qBAAqB,CACjC,QAAQ,EAAE,mBAAmB,EAC7B,OAAO,EAAE;IAAC,MAAM,EAAE,MAAM,CAAC;IAAC,OAAO,CAAC,EAAE,MAAM,CAAA;CAAC,GAC5C,eAAe,CAYjB;AAED,wBAAgB,sBAAsB,CAClC,QAAQ,EAAE,mBAAmB,EAC7B,OAAO,EAAE;IAAC,MAAM,EAAE,MAAM,CAAC;IAAC,OAAO,CAAC,EAAE,MAAM,CAAA;CAAC,GAC5C,MAAM,EAAE,CAYV;AAED,wBAAgB,mBAAmB,CAC/B,QAAQ,EAAE,mBAAmB,EAC7B,OAAO,EAAE;IAAC,MAAM,EAAE,MAAM,CAAC;IAAC,OAAO,CAAC,EAAE,MAAM,CAAA;CAAC,GAC5C,MAAM,EAAE,CAYV;AAED,wBAAgB,kBAAkB,IAAI,IAAI,CAEzC"}