@jterrats/smart-deployment 1.0.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +193 -0
- package/lib/ai/agentforce-error-handler.d.ts +81 -0
- package/lib/ai/agentforce-error-handler.js +196 -0
- package/lib/ai/agentforce-error-handler.js.map +1 -0
- package/lib/ai/agentforce-priority-service.d.ts +82 -0
- package/lib/ai/agentforce-priority-service.js +257 -0
- package/lib/ai/agentforce-priority-service.js.map +1 -0
- package/lib/ai/agentforce-service.d.ts +99 -0
- package/lib/ai/agentforce-service.js +300 -0
- package/lib/ai/agentforce-service.js.map +1 -0
- package/lib/ai/circuit-breaker.d.ts +115 -0
- package/lib/ai/circuit-breaker.js +277 -0
- package/lib/ai/circuit-breaker.js.map +1 -0
- package/lib/ai/dependency-inference-service.d.ts +76 -0
- package/lib/ai/dependency-inference-service.js +220 -0
- package/lib/ai/dependency-inference-service.js.map +1 -0
- package/lib/ai/llm-provider-factory.d.ts +15 -0
- package/lib/ai/llm-provider-factory.js +36 -0
- package/lib/ai/llm-provider-factory.js.map +1 -0
- package/lib/ai/llm-provider.d.ts +27 -0
- package/lib/ai/llm-provider.js +2 -0
- package/lib/ai/llm-provider.js.map +1 -0
- package/lib/ai/openai-service.d.ts +20 -0
- package/lib/ai/openai-service.js +89 -0
- package/lib/ai/openai-service.js.map +1 -0
- package/lib/ai/prompt-builder.d.ts +79 -0
- package/lib/ai/prompt-builder.js +180 -0
- package/lib/ai/prompt-builder.js.map +1 -0
- package/lib/ai/response-parser.d.ts +67 -0
- package/lib/ai/response-parser.js +234 -0
- package/lib/ai/response-parser.js.map +1 -0
- package/lib/ai/wave-validation-service.d.ts +111 -0
- package/lib/ai/wave-validation-service.js +381 -0
- package/lib/ai/wave-validation-service.js.map +1 -0
- package/lib/analysis/analysis-reporter.d.ts +56 -0
- package/lib/analysis/analysis-reporter.js +170 -0
- package/lib/analysis/analysis-reporter.js.map +1 -0
- package/lib/analytics/error-analytics.d.ts +80 -0
- package/lib/analytics/error-analytics.js +162 -0
- package/lib/analytics/error-analytics.js.map +1 -0
- package/lib/commands/analyze.d.ts +49 -0
- package/lib/commands/analyze.js +232 -0
- package/lib/commands/analyze.js.map +1 -0
- package/lib/commands/config.d.ts +42 -0
- package/lib/commands/config.js +219 -0
- package/lib/commands/config.js.map +1 -0
- package/lib/commands/resume.d.ts +26 -0
- package/lib/commands/resume.js +69 -0
- package/lib/commands/resume.js.map +1 -0
- package/lib/commands/start.d.ts +70 -0
- package/lib/commands/start.js +659 -0
- package/lib/commands/start.js.map +1 -0
- package/lib/commands/status.d.ts +37 -0
- package/lib/commands/status.js +69 -0
- package/lib/commands/status.js.map +1 -0
- package/lib/commands/validate.d.ts +33 -0
- package/lib/commands/validate.js +66 -0
- package/lib/commands/validate.js.map +1 -0
- package/lib/config/repo-config.d.ts +22 -0
- package/lib/config/repo-config.js +31 -0
- package/lib/config/repo-config.js.map +1 -0
- package/lib/constants/agentforce-limits.d.ts +174 -0
- package/lib/constants/agentforce-limits.js +262 -0
- package/lib/constants/agentforce-limits.js.map +1 -0
- package/lib/constants/api-version.d.ts +70 -0
- package/lib/constants/api-version.js +122 -0
- package/lib/constants/api-version.js.map +1 -0
- package/lib/constants/deployment-order.d.ts +68 -0
- package/lib/constants/deployment-order.js +162 -0
- package/lib/constants/deployment-order.js.map +1 -0
- package/lib/constants/salesforce-limits.d.ts +107 -0
- package/lib/constants/salesforce-limits.js +104 -0
- package/lib/constants/salesforce-limits.js.map +1 -0
- package/lib/dependencies/circular-dependency-detector.d.ts +137 -0
- package/lib/dependencies/circular-dependency-detector.js +329 -0
- package/lib/dependencies/circular-dependency-detector.js.map +1 -0
- package/lib/dependencies/cycle-remediation-planner.d.ts +50 -0
- package/lib/dependencies/cycle-remediation-planner.js +192 -0
- package/lib/dependencies/cycle-remediation-planner.js.map +1 -0
- package/lib/dependencies/dependency-cache.d.ts +134 -0
- package/lib/dependencies/dependency-cache.js +303 -0
- package/lib/dependencies/dependency-cache.js.map +1 -0
- package/lib/dependencies/dependency-depth-calculator.d.ts +145 -0
- package/lib/dependencies/dependency-depth-calculator.js +368 -0
- package/lib/dependencies/dependency-depth-calculator.js.map +1 -0
- package/lib/dependencies/dependency-graph-builder.d.ts +151 -0
- package/lib/dependencies/dependency-graph-builder.js +411 -0
- package/lib/dependencies/dependency-graph-builder.js.map +1 -0
- package/lib/dependencies/dependency-impact-analyzer.d.ts +145 -0
- package/lib/dependencies/dependency-impact-analyzer.js +330 -0
- package/lib/dependencies/dependency-impact-analyzer.js.map +1 -0
- package/lib/dependencies/dependency-merger.d.ts +122 -0
- package/lib/dependencies/dependency-merger.js +245 -0
- package/lib/dependencies/dependency-merger.js.map +1 -0
- package/lib/dependencies/dependency-resolver.d.ts +157 -0
- package/lib/dependencies/dependency-resolver.js +298 -0
- package/lib/dependencies/dependency-resolver.js.map +1 -0
- package/lib/dependencies/dependency-validator.d.ts +123 -0
- package/lib/dependencies/dependency-validator.js +291 -0
- package/lib/dependencies/dependency-validator.js.map +1 -0
- package/lib/dependencies/graph-visualizer.d.ts +110 -0
- package/lib/dependencies/graph-visualizer.js +262 -0
- package/lib/dependencies/graph-visualizer.js.map +1 -0
- package/lib/dependencies/heuristic-inference.d.ts +136 -0
- package/lib/dependencies/heuristic-inference.js +430 -0
- package/lib/dependencies/heuristic-inference.js.map +1 -0
- package/lib/deployment/cycle-source-editor.d.ts +34 -0
- package/lib/deployment/cycle-source-editor.js +121 -0
- package/lib/deployment/cycle-source-editor.js.map +1 -0
- package/lib/deployment/deployment-error-handler.d.ts +38 -0
- package/lib/deployment/deployment-error-handler.js +79 -0
- package/lib/deployment/deployment-error-handler.js.map +1 -0
- package/lib/deployment/deployment-reporter.d.ts +63 -0
- package/lib/deployment/deployment-reporter.js +150 -0
- package/lib/deployment/deployment-reporter.js.map +1 -0
- package/lib/deployment/deployment-state-summary.d.ts +38 -0
- package/lib/deployment/deployment-state-summary.js +209 -0
- package/lib/deployment/deployment-state-summary.js.map +1 -0
- package/lib/deployment/deployment-status-service.d.ts +36 -0
- package/lib/deployment/deployment-status-service.js +128 -0
- package/lib/deployment/deployment-status-service.js.map +1 -0
- package/lib/deployment/deployment-tracker.d.ts +42 -0
- package/lib/deployment/deployment-tracker.js +79 -0
- package/lib/deployment/deployment-tracker.js.map +1 -0
- package/lib/deployment/deployment-validation-service.d.ts +28 -0
- package/lib/deployment/deployment-validation-service.js +161 -0
- package/lib/deployment/deployment-validation-service.js.map +1 -0
- package/lib/deployment/retry-handler.d.ts +37 -0
- package/lib/deployment/retry-handler.js +86 -0
- package/lib/deployment/retry-handler.js.map +1 -0
- package/lib/deployment/sf-cli-integration.d.ts +42 -0
- package/lib/deployment/sf-cli-integration.js +105 -0
- package/lib/deployment/sf-cli-integration.js.map +1 -0
- package/lib/deployment/state-manager.d.ts +61 -0
- package/lib/deployment/state-manager.js +83 -0
- package/lib/deployment/state-manager.js.map +1 -0
- package/lib/deployment/test-executor.d.ts +41 -0
- package/lib/deployment/test-executor.js +87 -0
- package/lib/deployment/test-executor.js.map +1 -0
- package/lib/errors/base-error.d.ts +24 -0
- package/lib/errors/base-error.js +66 -0
- package/lib/errors/base-error.js.map +1 -0
- package/lib/errors/dependency-error.d.ts +37 -0
- package/lib/errors/dependency-error.js +76 -0
- package/lib/errors/dependency-error.js.map +1 -0
- package/lib/errors/deployment-error.d.ts +55 -0
- package/lib/errors/deployment-error.js +132 -0
- package/lib/errors/deployment-error.js.map +1 -0
- package/lib/errors/index.d.ts +45 -0
- package/lib/errors/index.js +71 -0
- package/lib/errors/index.js.map +1 -0
- package/lib/errors/network-error.d.ts +53 -0
- package/lib/errors/network-error.js +111 -0
- package/lib/errors/network-error.js.map +1 -0
- package/lib/errors/parsing-error.d.ts +41 -0
- package/lib/errors/parsing-error.js +69 -0
- package/lib/errors/parsing-error.js.map +1 -0
- package/lib/errors/validation-error-reporter.d.ts +34 -0
- package/lib/errors/validation-error-reporter.js +99 -0
- package/lib/errors/validation-error-reporter.js.map +1 -0
- package/lib/errors/validation-error.d.ts +58 -0
- package/lib/errors/validation-error.js +131 -0
- package/lib/errors/validation-error.js.map +1 -0
- package/lib/index.d.ts +2 -0
- package/lib/index.js +2 -0
- package/lib/index.js.map +1 -0
- package/lib/monitoring/performance-monitor.d.ts +98 -0
- package/lib/monitoring/performance-monitor.js +260 -0
- package/lib/monitoring/performance-monitor.js.map +1 -0
- package/lib/parsers/apex-class-parser.d.ts +47 -0
- package/lib/parsers/apex-class-parser.js +368 -0
- package/lib/parsers/apex-class-parser.js.map +1 -0
- package/lib/parsers/apex-trigger-parser.d.ts +48 -0
- package/lib/parsers/apex-trigger-parser.js +229 -0
- package/lib/parsers/apex-trigger-parser.js.map +1 -0
- package/lib/parsers/aura-parser.d.ts +55 -0
- package/lib/parsers/aura-parser.js +229 -0
- package/lib/parsers/aura-parser.js.map +1 -0
- package/lib/parsers/bot-parser.d.ts +65 -0
- package/lib/parsers/bot-parser.js +225 -0
- package/lib/parsers/bot-parser.js.map +1 -0
- package/lib/parsers/custom-metadata-parser.d.ts +94 -0
- package/lib/parsers/custom-metadata-parser.js +199 -0
- package/lib/parsers/custom-metadata-parser.js.map +1 -0
- package/lib/parsers/custom-object-parser.d.ts +62 -0
- package/lib/parsers/custom-object-parser.js +297 -0
- package/lib/parsers/custom-object-parser.js.map +1 -0
- package/lib/parsers/email-template-parser.d.ts +64 -0
- package/lib/parsers/email-template-parser.js +238 -0
- package/lib/parsers/email-template-parser.js.map +1 -0
- package/lib/parsers/error-resilient-parser.d.ts +110 -0
- package/lib/parsers/error-resilient-parser.js +277 -0
- package/lib/parsers/error-resilient-parser.js.map +1 -0
- package/lib/parsers/flexipage-parser.d.ts +64 -0
- package/lib/parsers/flexipage-parser.js +196 -0
- package/lib/parsers/flexipage-parser.js.map +1 -0
- package/lib/parsers/flow-parser.d.ts +54 -0
- package/lib/parsers/flow-parser.js +287 -0
- package/lib/parsers/flow-parser.js.map +1 -0
- package/lib/parsers/genai-prompt-parser.d.ts +67 -0
- package/lib/parsers/genai-prompt-parser.js +160 -0
- package/lib/parsers/genai-prompt-parser.js.map +1 -0
- package/lib/parsers/layout-parser.d.ts +64 -0
- package/lib/parsers/layout-parser.js +267 -0
- package/lib/parsers/layout-parser.js.map +1 -0
- package/lib/parsers/lwc-parser.d.ts +60 -0
- package/lib/parsers/lwc-parser.js +264 -0
- package/lib/parsers/lwc-parser.js.map +1 -0
- package/lib/parsers/permission-set-parser.d.ts +86 -0
- package/lib/parsers/permission-set-parser.js +152 -0
- package/lib/parsers/permission-set-parser.js.map +1 -0
- package/lib/parsers/profile-parser.d.ts +81 -0
- package/lib/parsers/profile-parser.js +141 -0
- package/lib/parsers/profile-parser.js.map +1 -0
- package/lib/parsers/visualforce-parser.d.ts +47 -0
- package/lib/parsers/visualforce-parser.js +180 -0
- package/lib/parsers/visualforce-parser.js.map +1 -0
- package/lib/provisioning/data-provisioner.d.ts +88 -0
- package/lib/provisioning/data-provisioner.js +257 -0
- package/lib/provisioning/data-provisioner.js.map +1 -0
- package/lib/scanner/custom-structure-scanner.d.ts +66 -0
- package/lib/scanner/custom-structure-scanner.js +229 -0
- package/lib/scanner/custom-structure-scanner.js.map +1 -0
- package/lib/scanner/forceignore-parser.d.ts +69 -0
- package/lib/scanner/forceignore-parser.js +195 -0
- package/lib/scanner/forceignore-parser.js.map +1 -0
- package/lib/scanner/metadata-format-scanner.d.ts +77 -0
- package/lib/scanner/metadata-format-scanner.js +282 -0
- package/lib/scanner/metadata-format-scanner.js.map +1 -0
- package/lib/scanner/monorepo-scanner.d.ts +71 -0
- package/lib/scanner/monorepo-scanner.js +225 -0
- package/lib/scanner/monorepo-scanner.js.map +1 -0
- package/lib/scanner/project-validator.d.ts +55 -0
- package/lib/scanner/project-validator.js +235 -0
- package/lib/scanner/project-validator.js.map +1 -0
- package/lib/scanner/sfdx-project-detector.d.ts +86 -0
- package/lib/scanner/sfdx-project-detector.js +240 -0
- package/lib/scanner/sfdx-project-detector.js.map +1 -0
- package/lib/scanner/structure-validator.d.ts +64 -0
- package/lib/scanner/structure-validator.js +296 -0
- package/lib/scanner/structure-validator.js.map +1 -0
- package/lib/services/metadata-scanner-service.d.ts +64 -0
- package/lib/services/metadata-scanner-service.js +651 -0
- package/lib/services/metadata-scanner-service.js.map +1 -0
- package/lib/types/agentforce.d.ts +157 -0
- package/lib/types/agentforce.js +2 -0
- package/lib/types/agentforce.js.map +1 -0
- package/lib/types/dependency.d.ts +98 -0
- package/lib/types/dependency.js +5 -0
- package/lib/types/dependency.js.map +1 -0
- package/lib/types/deployment-plan.d.ts +81 -0
- package/lib/types/deployment-plan.js +6 -0
- package/lib/types/deployment-plan.js.map +1 -0
- package/lib/types/deployment.d.ts +88 -0
- package/lib/types/deployment.js +5 -0
- package/lib/types/deployment.js.map +1 -0
- package/lib/types/graph.d.ts +35 -0
- package/lib/types/graph.js +5 -0
- package/lib/types/graph.js.map +1 -0
- package/lib/types/index.d.ts +12 -0
- package/lib/types/index.js +17 -0
- package/lib/types/index.js.map +1 -0
- package/lib/types/metadata.d.ts +101 -0
- package/lib/types/metadata.js +13 -0
- package/lib/types/metadata.js.map +1 -0
- package/lib/types/project.d.ts +156 -0
- package/lib/types/project.js +56 -0
- package/lib/types/project.js.map +1 -0
- package/lib/types/salesforce/apex.d.ts +94 -0
- package/lib/types/salesforce/apex.js +6 -0
- package/lib/types/salesforce/apex.js.map +1 -0
- package/lib/types/salesforce/aura.d.ts +150 -0
- package/lib/types/salesforce/aura.js +6 -0
- package/lib/types/salesforce/aura.js.map +1 -0
- package/lib/types/salesforce/bot.d.ts +293 -0
- package/lib/types/salesforce/bot.js +6 -0
- package/lib/types/salesforce/bot.js.map +1 -0
- package/lib/types/salesforce/common.d.ts +15 -0
- package/lib/types/salesforce/common.js +5 -0
- package/lib/types/salesforce/common.js.map +1 -0
- package/lib/types/salesforce/custom-metadata.d.ts +92 -0
- package/lib/types/salesforce/custom-metadata.js +6 -0
- package/lib/types/salesforce/custom-metadata.js.map +1 -0
- package/lib/types/salesforce/email.d.ts +56 -0
- package/lib/types/salesforce/email.js +6 -0
- package/lib/types/salesforce/email.js.map +1 -0
- package/lib/types/salesforce/flexipage.d.ts +149 -0
- package/lib/types/salesforce/flexipage.js +6 -0
- package/lib/types/salesforce/flexipage.js.map +1 -0
- package/lib/types/salesforce/flow.d.ts +516 -0
- package/lib/types/salesforce/flow.js +6 -0
- package/lib/types/salesforce/flow.js.map +1 -0
- package/lib/types/salesforce/genai.d.ts +67 -0
- package/lib/types/salesforce/genai.js +6 -0
- package/lib/types/salesforce/genai.js.map +1 -0
- package/lib/types/salesforce/index.d.ts +27 -0
- package/lib/types/salesforce/index.js +43 -0
- package/lib/types/salesforce/index.js.map +1 -0
- package/lib/types/salesforce/layout.d.ts +236 -0
- package/lib/types/salesforce/layout.js +6 -0
- package/lib/types/salesforce/layout.js.map +1 -0
- package/lib/types/salesforce/lwc.d.ts +123 -0
- package/lib/types/salesforce/lwc.js +6 -0
- package/lib/types/salesforce/lwc.js.map +1 -0
- package/lib/types/salesforce/object.d.ts +427 -0
- package/lib/types/salesforce/object.js +6 -0
- package/lib/types/salesforce/object.js.map +1 -0
- package/lib/types/salesforce/parser-types.d.ts +79 -0
- package/lib/types/salesforce/parser-types.js +80 -0
- package/lib/types/salesforce/parser-types.js.map +1 -0
- package/lib/types/salesforce/permission.d.ts +289 -0
- package/lib/types/salesforce/permission.js +6 -0
- package/lib/types/salesforce/permission.js.map +1 -0
- package/lib/types/salesforce/resource.d.ts +93 -0
- package/lib/types/salesforce/resource.js +6 -0
- package/lib/types/salesforce/resource.js.map +1 -0
- package/lib/types/salesforce/visualforce.d.ts +70 -0
- package/lib/types/salesforce/visualforce.js +6 -0
- package/lib/types/salesforce/visualforce.js.map +1 -0
- package/lib/utils/cache-manager.d.ts +158 -0
- package/lib/utils/cache-manager.js +429 -0
- package/lib/utils/cache-manager.js.map +1 -0
- package/lib/utils/deployment-plan-manager.d.ts +40 -0
- package/lib/utils/deployment-plan-manager.js +183 -0
- package/lib/utils/deployment-plan-manager.js.map +1 -0
- package/lib/utils/error-aggregator.d.ts +117 -0
- package/lib/utils/error-aggregator.js +268 -0
- package/lib/utils/error-aggregator.js.map +1 -0
- package/lib/utils/file-system.d.ts +62 -0
- package/lib/utils/file-system.js +167 -0
- package/lib/utils/file-system.js.map +1 -0
- package/lib/utils/functional.d.ts +52 -0
- package/lib/utils/functional.js +61 -0
- package/lib/utils/functional.js.map +1 -0
- package/lib/utils/graph-algorithms.d.ts +53 -0
- package/lib/utils/graph-algorithms.js +177 -0
- package/lib/utils/graph-algorithms.js.map +1 -0
- package/lib/utils/logger.d.ts +154 -0
- package/lib/utils/logger.js +327 -0
- package/lib/utils/logger.js.map +1 -0
- package/lib/utils/network-handler.d.ts +64 -0
- package/lib/utils/network-handler.js +147 -0
- package/lib/utils/network-handler.js.map +1 -0
- package/lib/utils/performance.d.ts +148 -0
- package/lib/utils/performance.js +294 -0
- package/lib/utils/performance.js.map +1 -0
- package/lib/utils/string.d.ts +197 -0
- package/lib/utils/string.js +331 -0
- package/lib/utils/string.js.map +1 -0
- package/lib/utils/xml.d.ts +97 -0
- package/lib/utils/xml.js +227 -0
- package/lib/utils/xml.js.map +1 -0
- package/lib/validators/xml-metadata-validator.d.ts +106 -0
- package/lib/validators/xml-metadata-validator.js +509 -0
- package/lib/validators/xml-metadata-validator.js.map +1 -0
- package/lib/waves/priority-wave-generator-ai.d.ts +85 -0
- package/lib/waves/priority-wave-generator-ai.js +191 -0
- package/lib/waves/priority-wave-generator-ai.js.map +1 -0
- package/lib/waves/priority-wave-generator.d.ts +47 -0
- package/lib/waves/priority-wave-generator.js +88 -0
- package/lib/waves/priority-wave-generator.js.map +1 -0
- package/lib/waves/test-optimizer.d.ts +155 -0
- package/lib/waves/test-optimizer.js +290 -0
- package/lib/waves/test-optimizer.js.map +1 -0
- package/lib/waves/wave-builder.d.ts +147 -0
- package/lib/waves/wave-builder.js +286 -0
- package/lib/waves/wave-builder.js.map +1 -0
- package/lib/waves/wave-diff-generator.d.ts +17 -0
- package/lib/waves/wave-diff-generator.js +6 -0
- package/lib/waves/wave-diff-generator.js.map +1 -0
- package/lib/waves/wave-executor.d.ts +33 -0
- package/lib/waves/wave-executor.js +50 -0
- package/lib/waves/wave-executor.js.map +1 -0
- package/lib/waves/wave-merger.d.ts +96 -0
- package/lib/waves/wave-merger.js +181 -0
- package/lib/waves/wave-merger.js.map +1 -0
- package/lib/waves/wave-metadata-generator.d.ts +13 -0
- package/lib/waves/wave-metadata-generator.js +12 -0
- package/lib/waves/wave-metadata-generator.js.map +1 -0
- package/lib/waves/wave-splitter.d.ts +154 -0
- package/lib/waves/wave-splitter.js +307 -0
- package/lib/waves/wave-splitter.js.map +1 -0
- package/lib/waves/wave-validator.d.ts +17 -0
- package/lib/waves/wave-validator.js +15 -0
- package/lib/waves/wave-validator.js.map +1 -0
- package/messages/analyze.json +18 -0
- package/messages/config.json +29 -0
- package/messages/resume.json +9 -0
- package/messages/start.json +24 -0
- package/messages/status.json +8 -0
- package/messages/validate.json +9 -0
- package/npm-shrinkwrap.json +25676 -0
- package/oclif.lock +11988 -0
- package/oclif.manifest.json +589 -0
- package/package.json +224 -0
|
@@ -0,0 +1,286 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Wave Builder
|
|
3
|
+
* Generates deployment waves using topological sort
|
|
4
|
+
*
|
|
5
|
+
* @ac US-038-AC-1: Generate waves from dependency graph
|
|
6
|
+
* @ac US-038-AC-2: Each wave contains independent components
|
|
7
|
+
* @ac US-038-AC-3: Components in wave N don't depend on wave N+1
|
|
8
|
+
* @ac US-038-AC-4: Handle components with no dependencies (wave 1)
|
|
9
|
+
* @ac US-038-AC-5: Handle isolated components
|
|
10
|
+
* @ac US-038-AC-6: Generate wave metadata
|
|
11
|
+
*
|
|
12
|
+
* @issue #38
|
|
13
|
+
*/
|
|
14
|
+
import { getLogger } from '../utils/logger.js';
|
|
15
|
+
const logger = getLogger('WaveBuilder');
|
|
16
|
+
/**
|
|
17
|
+
* Metadata type deployment order (Salesforce recommended)
|
|
18
|
+
*/
|
|
19
|
+
const TYPE_DEPLOYMENT_ORDER = [
|
|
20
|
+
'CustomObject',
|
|
21
|
+
'CustomField',
|
|
22
|
+
'RecordType',
|
|
23
|
+
'BusinessProcess',
|
|
24
|
+
'CompactLayout',
|
|
25
|
+
'Layout',
|
|
26
|
+
'Profile',
|
|
27
|
+
'PermissionSet',
|
|
28
|
+
'ApexClass',
|
|
29
|
+
'ApexTrigger',
|
|
30
|
+
'Flow',
|
|
31
|
+
'ValidationRule',
|
|
32
|
+
'WorkflowRule',
|
|
33
|
+
'EmailTemplate',
|
|
34
|
+
'FlexiPage',
|
|
35
|
+
];
|
|
36
|
+
/**
|
|
37
|
+
* Wave Builder
|
|
38
|
+
*
|
|
39
|
+
* Generates deployment waves using topological sort algorithm.
|
|
40
|
+
* Each wave contains components that can be deployed in parallel.
|
|
41
|
+
*
|
|
42
|
+
* Algorithm:
|
|
43
|
+
* 1. Calculate in-degree for all nodes
|
|
44
|
+
* 2. Add nodes with in-degree 0 to first wave
|
|
45
|
+
* 3. Remove those nodes and update in-degrees
|
|
46
|
+
* 4. Repeat until all nodes are placed
|
|
47
|
+
*
|
|
48
|
+
* Performance: O(V + E)
|
|
49
|
+
*
|
|
50
|
+
* @example
|
|
51
|
+
* const builder = new WaveBuilder({
|
|
52
|
+
* maxComponentsPerWave: 10000,
|
|
53
|
+
* respectTypeOrder: true
|
|
54
|
+
* });
|
|
55
|
+
*
|
|
56
|
+
* const result = builder.generateWaves(graph);
|
|
57
|
+
* console.log(`Generated ${result.waves.length} waves`);
|
|
58
|
+
*/
|
|
59
|
+
export class WaveBuilder {
|
|
60
|
+
options;
|
|
61
|
+
constructor(options = {}) {
|
|
62
|
+
this.options = {
|
|
63
|
+
maxComponentsPerWave: options.maxComponentsPerWave ?? 0,
|
|
64
|
+
respectTypeOrder: options.respectTypeOrder ?? true,
|
|
65
|
+
handleCircularDeps: options.handleCircularDeps ?? true,
|
|
66
|
+
};
|
|
67
|
+
logger.debug('Initialized WaveBuilder', {
|
|
68
|
+
maxComponentsPerWave: this.options.maxComponentsPerWave,
|
|
69
|
+
respectTypeOrder: this.options.respectTypeOrder,
|
|
70
|
+
});
|
|
71
|
+
}
|
|
72
|
+
/**
|
|
73
|
+
* @ac US-038-AC-1: Generate waves from dependency graph
|
|
74
|
+
* @ac US-038-AC-2: Each wave contains independent components
|
|
75
|
+
* @ac US-038-AC-3: Components in wave N don't depend on wave N+1
|
|
76
|
+
*/
|
|
77
|
+
generateWaves(graph) {
|
|
78
|
+
const startTime = Date.now();
|
|
79
|
+
// Calculate in-degree for all nodes
|
|
80
|
+
const inDegree = this.calculateInDegree(graph);
|
|
81
|
+
const waves = [];
|
|
82
|
+
const processed = new Set();
|
|
83
|
+
const unplacedComponents = [];
|
|
84
|
+
let waveNumber = 1;
|
|
85
|
+
// Build waves using topological sort
|
|
86
|
+
while (processed.size < graph.size) {
|
|
87
|
+
// Find nodes with in-degree 0
|
|
88
|
+
const currentWave = [];
|
|
89
|
+
for (const [nodeId, degree] of inDegree.entries()) {
|
|
90
|
+
if (degree === 0 && !processed.has(nodeId)) {
|
|
91
|
+
currentWave.push(nodeId);
|
|
92
|
+
}
|
|
93
|
+
}
|
|
94
|
+
// No progress - circular dependency
|
|
95
|
+
if (currentWave.length === 0) {
|
|
96
|
+
this.handleCircularWave(graph, processed, unplacedComponents, waves, waveNumber);
|
|
97
|
+
break;
|
|
98
|
+
}
|
|
99
|
+
// Sort by type order if configured
|
|
100
|
+
if (this.options.respectTypeOrder) {
|
|
101
|
+
currentWave.sort((a, b) => this.compareByTypeOrder(a, b));
|
|
102
|
+
}
|
|
103
|
+
// Split into multiple waves if exceeds max size
|
|
104
|
+
if (this.options.maxComponentsPerWave > 0 && currentWave.length > this.options.maxComponentsPerWave) {
|
|
105
|
+
const chunks = this.chunkArray(currentWave, this.options.maxComponentsPerWave);
|
|
106
|
+
for (const chunk of chunks) {
|
|
107
|
+
waves.push({
|
|
108
|
+
number: waveNumber++,
|
|
109
|
+
components: chunk,
|
|
110
|
+
metadata: this.generateWaveMetadata(chunk, false),
|
|
111
|
+
});
|
|
112
|
+
// Mark as processed
|
|
113
|
+
for (const nodeId of chunk) {
|
|
114
|
+
processed.add(nodeId);
|
|
115
|
+
}
|
|
116
|
+
}
|
|
117
|
+
}
|
|
118
|
+
else {
|
|
119
|
+
// Add wave
|
|
120
|
+
waves.push({
|
|
121
|
+
number: waveNumber++,
|
|
122
|
+
components: currentWave,
|
|
123
|
+
metadata: this.generateWaveMetadata(currentWave, false),
|
|
124
|
+
});
|
|
125
|
+
// Mark as processed
|
|
126
|
+
for (const nodeId of currentWave) {
|
|
127
|
+
processed.add(nodeId);
|
|
128
|
+
}
|
|
129
|
+
}
|
|
130
|
+
// Update in-degrees: reduce count for nodes that depended on current wave nodes
|
|
131
|
+
for (const [nodeId, deps] of graph.entries()) {
|
|
132
|
+
if (processed.has(nodeId))
|
|
133
|
+
continue;
|
|
134
|
+
// Count how many of its dependencies were in the current wave
|
|
135
|
+
let removedDeps = 0;
|
|
136
|
+
for (const dep of deps) {
|
|
137
|
+
if (currentWave.includes(dep)) {
|
|
138
|
+
removedDeps++;
|
|
139
|
+
}
|
|
140
|
+
}
|
|
141
|
+
if (removedDeps > 0) {
|
|
142
|
+
inDegree.set(nodeId, (inDegree.get(nodeId) ?? 0) - removedDeps);
|
|
143
|
+
}
|
|
144
|
+
}
|
|
145
|
+
}
|
|
146
|
+
// Calculate statistics
|
|
147
|
+
const stats = this.calculateStats(waves);
|
|
148
|
+
const duration = Date.now() - startTime;
|
|
149
|
+
logger.info('Wave generation completed', {
|
|
150
|
+
waves: waves.length,
|
|
151
|
+
components: processed.size,
|
|
152
|
+
unplaced: unplacedComponents.length,
|
|
153
|
+
durationMs: duration,
|
|
154
|
+
});
|
|
155
|
+
// Ensure waves are sorted by number before returning
|
|
156
|
+
waves.sort((a, b) => a.number - b.number);
|
|
157
|
+
return {
|
|
158
|
+
waves,
|
|
159
|
+
totalComponents: graph.size,
|
|
160
|
+
unplacedComponents,
|
|
161
|
+
circularDependencies: [],
|
|
162
|
+
stats,
|
|
163
|
+
};
|
|
164
|
+
}
|
|
165
|
+
/**
|
|
166
|
+
* Calculate in-degree for all nodes
|
|
167
|
+
* In-degree = number of dependencies this node has (how many nodes it depends on)
|
|
168
|
+
* Nodes with in-degree 0 have no dependencies and can be deployed first
|
|
169
|
+
*/
|
|
170
|
+
calculateInDegree(graph) {
|
|
171
|
+
const inDegree = new Map();
|
|
172
|
+
// Initialize all nodes with their dependency count
|
|
173
|
+
for (const [nodeId, deps] of graph.entries()) {
|
|
174
|
+
inDegree.set(nodeId, deps.size);
|
|
175
|
+
}
|
|
176
|
+
return inDegree;
|
|
177
|
+
}
|
|
178
|
+
handleCircularWave(graph, processed, unplacedComponents, waves, waveNumber) {
|
|
179
|
+
const remaining = this.collectRemainingNodes(graph, processed);
|
|
180
|
+
unplacedComponents.push(...remaining);
|
|
181
|
+
logger.warn('Circular dependencies detected', {
|
|
182
|
+
remaining: remaining.length,
|
|
183
|
+
});
|
|
184
|
+
if (this.options.handleCircularDeps) {
|
|
185
|
+
waves.push({
|
|
186
|
+
number: waveNumber,
|
|
187
|
+
components: remaining,
|
|
188
|
+
metadata: this.generateWaveMetadata(remaining, true),
|
|
189
|
+
});
|
|
190
|
+
}
|
|
191
|
+
}
|
|
192
|
+
collectRemainingNodes(graph, processed) {
|
|
193
|
+
const remaining = [];
|
|
194
|
+
for (const nodeId of graph.keys()) {
|
|
195
|
+
if (!processed.has(nodeId)) {
|
|
196
|
+
remaining.push(nodeId);
|
|
197
|
+
}
|
|
198
|
+
}
|
|
199
|
+
return remaining;
|
|
200
|
+
}
|
|
201
|
+
/**
|
|
202
|
+
* @ac US-038-AC-6: Generate wave metadata
|
|
203
|
+
*/
|
|
204
|
+
generateWaveMetadata(components, hasCircularDeps) {
|
|
205
|
+
const types = new Set();
|
|
206
|
+
const maxDepth = 0;
|
|
207
|
+
for (const component of components) {
|
|
208
|
+
const [type] = component.split(':');
|
|
209
|
+
types.add(type);
|
|
210
|
+
}
|
|
211
|
+
// Estimate deployment time (rough estimate: 0.1s per component)
|
|
212
|
+
const estimatedTime = Math.ceil(components.length * 0.1);
|
|
213
|
+
return {
|
|
214
|
+
componentCount: components.length,
|
|
215
|
+
types: Array.from(types),
|
|
216
|
+
maxDepth,
|
|
217
|
+
hasCircularDeps,
|
|
218
|
+
estimatedTime,
|
|
219
|
+
};
|
|
220
|
+
}
|
|
221
|
+
/**
|
|
222
|
+
* Compare nodes by type deployment order
|
|
223
|
+
*/
|
|
224
|
+
compareByTypeOrder(a, b) {
|
|
225
|
+
const typeA = a.split(':')[0];
|
|
226
|
+
const typeB = b.split(':')[0];
|
|
227
|
+
const orderA = TYPE_DEPLOYMENT_ORDER.indexOf(typeA);
|
|
228
|
+
const orderB = TYPE_DEPLOYMENT_ORDER.indexOf(typeB);
|
|
229
|
+
// If not in order list, put at end
|
|
230
|
+
const finalOrderA = orderA === -1 ? 9999 : orderA;
|
|
231
|
+
const finalOrderB = orderB === -1 ? 9999 : orderB;
|
|
232
|
+
return finalOrderA - finalOrderB;
|
|
233
|
+
}
|
|
234
|
+
/**
|
|
235
|
+
* Split array into chunks
|
|
236
|
+
*/
|
|
237
|
+
chunkArray(array, chunkSize) {
|
|
238
|
+
const chunks = [];
|
|
239
|
+
for (let i = 0; i < array.length; i += chunkSize) {
|
|
240
|
+
chunks.push(array.slice(i, i + chunkSize));
|
|
241
|
+
}
|
|
242
|
+
return chunks;
|
|
243
|
+
}
|
|
244
|
+
/**
|
|
245
|
+
* Calculate wave statistics
|
|
246
|
+
*/
|
|
247
|
+
calculateStats(waves) {
|
|
248
|
+
if (waves.length === 0) {
|
|
249
|
+
return {
|
|
250
|
+
totalWaves: 0,
|
|
251
|
+
avgComponentsPerWave: 0,
|
|
252
|
+
largestWaveSize: 0,
|
|
253
|
+
smallestWaveSize: 0,
|
|
254
|
+
totalEstimatedTime: 0,
|
|
255
|
+
};
|
|
256
|
+
}
|
|
257
|
+
const sizes = waves.map((w) => w.components.length);
|
|
258
|
+
const totalComponents = sizes.reduce((sum, size) => sum + size, 0);
|
|
259
|
+
const totalTime = waves.reduce((sum, w) => sum + w.metadata.estimatedTime, 0);
|
|
260
|
+
return {
|
|
261
|
+
totalWaves: waves.length,
|
|
262
|
+
avgComponentsPerWave: Math.round(totalComponents / waves.length),
|
|
263
|
+
largestWaveSize: Math.max(...sizes),
|
|
264
|
+
smallestWaveSize: Math.min(...sizes),
|
|
265
|
+
totalEstimatedTime: totalTime,
|
|
266
|
+
};
|
|
267
|
+
}
|
|
268
|
+
/**
|
|
269
|
+
* Get wave by number
|
|
270
|
+
*/
|
|
271
|
+
getWave(result, waveNumber) {
|
|
272
|
+
return result.waves.find((w) => w.number === waveNumber);
|
|
273
|
+
}
|
|
274
|
+
/**
|
|
275
|
+
* Get component wave number
|
|
276
|
+
*/
|
|
277
|
+
getComponentWave(result, componentId) {
|
|
278
|
+
for (const wave of result.waves) {
|
|
279
|
+
if (wave.components.includes(componentId)) {
|
|
280
|
+
return wave.number;
|
|
281
|
+
}
|
|
282
|
+
}
|
|
283
|
+
return undefined;
|
|
284
|
+
}
|
|
285
|
+
}
|
|
286
|
+
//# sourceMappingURL=wave-builder.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"wave-builder.js","sourceRoot":"","sources":["../../src/waves/wave-builder.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Wave Diff Generator - US-045
|
|
3
|
+
*
|
|
4
|
+
* @ac US-045-AC-1: Compare two wave generations
|
|
5
|
+
* @ac US-045-AC-2: Show added/removed components
|
|
6
|
+
* @ac US-045-AC-3: Show wave reordering
|
|
7
|
+
* @ac US-045-AC-4: Show dependency changes
|
|
8
|
+
* @issue #45
|
|
9
|
+
*/
|
|
10
|
+
import type { Wave } from './wave-builder.js';
|
|
11
|
+
export declare class WaveDiffGenerator {
|
|
12
|
+
generateDiff(oldWaves: Wave[], newWaves: Wave[]): {
|
|
13
|
+
added: string[];
|
|
14
|
+
removed: string[];
|
|
15
|
+
reordered: boolean;
|
|
16
|
+
};
|
|
17
|
+
}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"wave-diff-generator.js","sourceRoot":"","sources":["../../src/waves/wave-diff-generator.ts"],"names":[],"mappings":"AAWA,MAAM,OAAO,iBAAiB;IACrB,YAAY,CACjB,QAAgB,EAChB,QAAgB;QAMhB,OAAO,EAAE,KAAK,EAAE,EAAE,EAAE,OAAO,EAAE,EAAE,EAAE,SAAS,EAAE,QAAQ,CAAC,MAAM,KAAK,QAAQ,CAAC,MAAM,EAAE,CAAC;IACpF,CAAC;CACF"}
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Wave Executor Utilities
|
|
3
|
+
* Ensures waves are executed in correct numerical order
|
|
4
|
+
*
|
|
5
|
+
* @ac Wave ordering fix: Ensure numerical execution order
|
|
6
|
+
*/
|
|
7
|
+
import type { Wave, WaveResult } from './wave-builder.js';
|
|
8
|
+
/**
|
|
9
|
+
* Sort waves by numerical order (not alphabetical)
|
|
10
|
+
*
|
|
11
|
+
* @example sortWavesByNumber({ waves: [wave10, wave2, wave1] }) => [wave1, wave2, wave10]
|
|
12
|
+
*/
|
|
13
|
+
export declare function sortWavesByNumber(result: WaveResult): Wave[];
|
|
14
|
+
/**
|
|
15
|
+
* Get waves in execution order (numerically sorted)
|
|
16
|
+
*/
|
|
17
|
+
export declare function getWavesInExecutionOrder(result: WaveResult): Wave[];
|
|
18
|
+
/**
|
|
19
|
+
* Format wave ID with zero-padding for consistent alphabetical sorting
|
|
20
|
+
*
|
|
21
|
+
* @example formatWaveId(1, 15) => "wave-001"
|
|
22
|
+
*/
|
|
23
|
+
export declare function formatWaveId(waveNumber: number, totalWaves: number): string;
|
|
24
|
+
/**
|
|
25
|
+
* Parse wave ID back to number
|
|
26
|
+
*
|
|
27
|
+
* @example parseWaveId("wave-001") => 1
|
|
28
|
+
*/
|
|
29
|
+
export declare function parseWaveId(waveId: string): number | undefined;
|
|
30
|
+
/**
|
|
31
|
+
* Validate wave execution order
|
|
32
|
+
*/
|
|
33
|
+
export declare function validateWaveOrder(waves: Wave[]): boolean;
|
|
@@ -0,0 +1,50 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Wave Executor Utilities
|
|
3
|
+
* Ensures waves are executed in correct numerical order
|
|
4
|
+
*
|
|
5
|
+
* @ac Wave ordering fix: Ensure numerical execution order
|
|
6
|
+
*/
|
|
7
|
+
/**
|
|
8
|
+
* Sort waves by numerical order (not alphabetical)
|
|
9
|
+
*
|
|
10
|
+
* @example sortWavesByNumber({ waves: [wave10, wave2, wave1] }) => [wave1, wave2, wave10]
|
|
11
|
+
*/
|
|
12
|
+
export function sortWavesByNumber(result) {
|
|
13
|
+
return [...result.waves].sort((a, b) => a.number - b.number);
|
|
14
|
+
}
|
|
15
|
+
/**
|
|
16
|
+
* Get waves in execution order (numerically sorted)
|
|
17
|
+
*/
|
|
18
|
+
export function getWavesInExecutionOrder(result) {
|
|
19
|
+
return sortWavesByNumber(result);
|
|
20
|
+
}
|
|
21
|
+
/**
|
|
22
|
+
* Format wave ID with zero-padding for consistent alphabetical sorting
|
|
23
|
+
*
|
|
24
|
+
* @example formatWaveId(1, 15) => "wave-001"
|
|
25
|
+
*/
|
|
26
|
+
export function formatWaveId(waveNumber, totalWaves) {
|
|
27
|
+
const padding = Math.max(3, String(totalWaves).length);
|
|
28
|
+
return `wave-${String(waveNumber).padStart(padding, '0')}`;
|
|
29
|
+
}
|
|
30
|
+
/**
|
|
31
|
+
* Parse wave ID back to number
|
|
32
|
+
*
|
|
33
|
+
* @example parseWaveId("wave-001") => 1
|
|
34
|
+
*/
|
|
35
|
+
export function parseWaveId(waveId) {
|
|
36
|
+
const match = /^wave-(\d+)$/.exec(waveId);
|
|
37
|
+
return match ? Number.parseInt(match[1], 10) : undefined;
|
|
38
|
+
}
|
|
39
|
+
/**
|
|
40
|
+
* Validate wave execution order
|
|
41
|
+
*/
|
|
42
|
+
export function validateWaveOrder(waves) {
|
|
43
|
+
for (let i = 0; i < waves.length; i++) {
|
|
44
|
+
if (waves[i].number !== i + 1) {
|
|
45
|
+
return false;
|
|
46
|
+
}
|
|
47
|
+
}
|
|
48
|
+
return true;
|
|
49
|
+
}
|
|
50
|
+
//# sourceMappingURL=wave-executor.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"wave-executor.js","sourceRoot":"","sources":["../../src/waves/wave-executor.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAIH;;;;GAIG;AACH,MAAM,UAAU,iBAAiB,CAAC,MAAkB;IAClD,OAAO,CAAC,GAAG,MAAM,CAAC,KAAK,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,MAAM,GAAG,CAAC,CAAC,MAAM,CAAC,CAAC;AAC/D,CAAC;AAED;;GAEG;AACH,MAAM,UAAU,wBAAwB,CAAC,MAAkB;IACzD,OAAO,iBAAiB,CAAC,MAAM,CAAC,CAAC;AACnC,CAAC;AAED;;;;GAIG;AACH,MAAM,UAAU,YAAY,CAAC,UAAkB,EAAE,UAAkB;IACjE,MAAM,OAAO,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,MAAM,CAAC,UAAU,CAAC,CAAC,MAAM,CAAC,CAAC;IACvD,OAAO,QAAQ,MAAM,CAAC,UAAU,CAAC,CAAC,QAAQ,CAAC,OAAO,EAAE,GAAG,CAAC,EAAE,CAAC;AAC7D,CAAC;AAED;;;;GAIG;AACH,MAAM,UAAU,WAAW,CAAC,MAAc;IACxC,MAAM,KAAK,GAAG,cAAc,CAAC,IAAI,CAAC,MAAM,CAAC,CAAC;IAC1C,OAAO,KAAK,CAAC,CAAC,CAAC,MAAM,CAAC,QAAQ,CAAC,KAAK,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC;AAC3D,CAAC;AAED;;GAEG;AACH,MAAM,UAAU,iBAAiB,CAAC,KAAa;IAC7C,KAAK,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,GAAG,KAAK,CAAC,MAAM,EAAE,CAAC,EAAE,EAAE,CAAC;QACtC,IAAI,KAAK,CAAC,CAAC,CAAC,CAAC,MAAM,KAAK,CAAC,GAAG,CAAC,EAAE,CAAC;YAC9B,OAAO,KAAK,CAAC;QACf,CAAC;IACH,CAAC;IACD,OAAO,IAAI,CAAC;AACd,CAAC"}
|
|
@@ -0,0 +1,96 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Wave Merger
|
|
3
|
+
* Merges small adjacent waves to reduce total deployment time
|
|
4
|
+
*
|
|
5
|
+
* @ac US-041-AC-1: Identify waves with <50 components
|
|
6
|
+
* @ac US-041-AC-2: Merge if combined < 300 components
|
|
7
|
+
* @ac US-041-AC-3: Respect dependency order
|
|
8
|
+
* @ac US-041-AC-4: Don't merge if different test requirements
|
|
9
|
+
* @ac US-041-AC-5: Report merge decisions
|
|
10
|
+
* @ac US-041-AC-6: User override option
|
|
11
|
+
*
|
|
12
|
+
* @issue #41
|
|
13
|
+
*/
|
|
14
|
+
import type { Wave } from './wave-builder.js';
|
|
15
|
+
/**
|
|
16
|
+
* Merge result
|
|
17
|
+
*/
|
|
18
|
+
export type MergeResult = {
|
|
19
|
+
originalWaves: Wave[];
|
|
20
|
+
mergedWaves: Wave[];
|
|
21
|
+
decisions: MergeDecision[];
|
|
22
|
+
stats: MergeStats;
|
|
23
|
+
};
|
|
24
|
+
/**
|
|
25
|
+
* Merge decision
|
|
26
|
+
*/
|
|
27
|
+
export type MergeDecision = {
|
|
28
|
+
mergedWaves: number[];
|
|
29
|
+
resultWaveNumber: number;
|
|
30
|
+
reason: string;
|
|
31
|
+
originalCount: number[];
|
|
32
|
+
mergedCount: number;
|
|
33
|
+
};
|
|
34
|
+
/**
|
|
35
|
+
* Merge statistics
|
|
36
|
+
*/
|
|
37
|
+
export type MergeStats = {
|
|
38
|
+
originalWaveCount: number;
|
|
39
|
+
mergedWaveCount: number;
|
|
40
|
+
wavesSaved: number;
|
|
41
|
+
componentsAffected: number;
|
|
42
|
+
};
|
|
43
|
+
/**
|
|
44
|
+
* Merger options
|
|
45
|
+
*/
|
|
46
|
+
export type MergerOptions = {
|
|
47
|
+
minComponentsForMerge?: number;
|
|
48
|
+
maxComponentsAfterMerge?: number;
|
|
49
|
+
respectTestRequirements?: boolean;
|
|
50
|
+
allowUserOverride?: boolean;
|
|
51
|
+
};
|
|
52
|
+
/**
|
|
53
|
+
* Wave Merger
|
|
54
|
+
*
|
|
55
|
+
* Merges small adjacent waves to reduce total deployment time.
|
|
56
|
+
*
|
|
57
|
+
* Algorithm:
|
|
58
|
+
* 1. Identify small waves (< threshold)
|
|
59
|
+
* 2. Check if adjacent waves can be merged
|
|
60
|
+
* 3. Validate no dependency violations
|
|
61
|
+
* 4. Merge waves and renumber
|
|
62
|
+
*
|
|
63
|
+
* Performance: O(V)
|
|
64
|
+
*
|
|
65
|
+
* @example
|
|
66
|
+
* const merger = new WaveMerger({
|
|
67
|
+
* minComponentsForMerge: 50,
|
|
68
|
+
* maxComponentsAfterMerge: 300
|
|
69
|
+
* });
|
|
70
|
+
*
|
|
71
|
+
* const result = merger.mergeWaves(waves, graph);
|
|
72
|
+
* console.log(`Saved ${result.stats.wavesSaved} waves`);
|
|
73
|
+
*/
|
|
74
|
+
export declare class WaveMerger {
|
|
75
|
+
private options;
|
|
76
|
+
constructor(options?: MergerOptions);
|
|
77
|
+
/**
|
|
78
|
+
* @ac US-041-AC-1: Identify waves with <50 components
|
|
79
|
+
* @ac US-041-AC-2: Merge if combined < 300 components
|
|
80
|
+
* @ac US-041-AC-3: Respect dependency order
|
|
81
|
+
* @ac US-041-AC-5: Report merge decisions
|
|
82
|
+
*/
|
|
83
|
+
mergeWaves(waves: Wave[], graph?: unknown): MergeResult;
|
|
84
|
+
/**
|
|
85
|
+
* Check if waves can be merged
|
|
86
|
+
*/
|
|
87
|
+
private canMerge;
|
|
88
|
+
/**
|
|
89
|
+
* Create merged wave
|
|
90
|
+
*/
|
|
91
|
+
private createMergedWave;
|
|
92
|
+
/**
|
|
93
|
+
* Generate merge report
|
|
94
|
+
*/
|
|
95
|
+
generateReport(result: MergeResult): string;
|
|
96
|
+
}
|