@tamyla/clodo-framework 3.1.21 → 3.1.22
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/CHANGELOG.md +9 -0
- package/README.md +53 -0
- package/dist/bin/clodo-service.js +47 -15
- package/dist/bin/commands/deploy.js +115 -83
- package/dist/bin/commands/helpers/deployment-ui.js +138 -0
- package/dist/bin/commands/helpers/deployment-verification.js +251 -0
- package/dist/bin/commands/helpers/error-recovery.js +80 -0
- package/dist/bin/commands/helpers/resource-detection.js +113 -0
- package/dist/bin/commands/validate.js +1 -1
- package/dist/bin/security/security-cli.js +1 -1
- package/dist/bin/shared/cache/configuration-cache.js +82 -0
- package/dist/bin/shared/cloudflare/domain-manager.js +1 -1
- package/dist/bin/shared/cloudflare/index.js +1 -1
- package/dist/bin/shared/cloudflare/ops.js +6 -4
- package/dist/bin/shared/config/ConfigurationManager.js +23 -1
- package/dist/bin/shared/config/command-config-manager.js +19 -3
- package/dist/bin/shared/config/index.js +1 -1
- package/dist/bin/shared/deployment/credential-collector.js +30 -7
- package/dist/bin/shared/deployment/index.js +2 -2
- package/dist/bin/shared/deployment/rollback-manager.js +4 -520
- package/dist/bin/shared/deployment/utilities/d1-error-recovery.js +177 -0
- package/dist/bin/shared/deployment/validator.js +40 -10
- package/dist/bin/shared/deployment/workflows/deployment-summary.js +214 -0
- package/dist/bin/shared/deployment/workflows/interactive-confirmation.js +188 -0
- package/dist/bin/shared/deployment/workflows/interactive-database-workflow.js +234 -0
- package/dist/bin/shared/deployment/workflows/interactive-domain-info-gatherer.js +240 -0
- package/dist/bin/shared/deployment/workflows/interactive-secret-workflow.js +228 -0
- package/dist/bin/shared/deployment/workflows/interactive-testing-workflow.js +235 -0
- package/dist/bin/shared/deployment/workflows/interactive-validation.js +218 -0
- package/dist/bin/shared/error-handling/error-classifier.js +46 -0
- package/dist/bin/shared/monitoring/health-checker.js +129 -1
- package/dist/bin/shared/monitoring/memory-manager.js +17 -6
- package/dist/bin/shared/routing/domain-router.js +1 -1
- package/dist/bin/shared/utils/deployment-validator.js +97 -0
- package/dist/bin/shared/utils/formatters.js +10 -0
- package/dist/bin/shared/utils/index.js +13 -1
- package/dist/bin/shared/utils/interactive-prompts.js +34 -18
- package/dist/bin/shared/utils/progress-manager.js +2 -2
- package/dist/bin/shared/utils/progress-spinner.js +53 -0
- package/dist/bin/shared/utils/sensitive-redactor.js +91 -0
- package/dist/bin/shared/validation/ValidationRegistry.js +1 -1
- package/dist/security/index.js +1 -1
- package/dist/security/patterns/insecure-patterns.js +1 -1
- package/dist/utils/constants.js +102 -0
- package/dist/utils/deployment/wrangler-config-manager.js +215 -48
- package/dist/utils/framework-config.js +2 -2
- package/dist/utils/interactive-prompts.js +10 -59
- package/package.json +16 -8
- package/dist/bin/clodo-service-old.js +0 -868
- package/dist/bin/clodo-service-test.js +0 -10
- package/dist/bin/commands/assess.js +0 -91
- package/dist/bin/commands/create.js +0 -77
- package/dist/bin/commands/diagnose.js +0 -83
- package/dist/bin/commands/helpers.js +0 -138
- package/dist/bin/commands/update.js +0 -75
- package/dist/bin/database/deployment-db-manager.js +0 -423
- package/dist/bin/database/enterprise-db-manager.js +0 -457
- package/dist/bin/database/wrangler-d1-manager.js +0 -685
- package/dist/bin/deployment/enterprise-deploy.js +0 -877
- package/dist/bin/deployment/master-deploy.js +0 -1376
- package/dist/bin/deployment/modular-enterprise-deploy.js +0 -466
- package/dist/bin/deployment/modules/DeploymentConfiguration.js +0 -395
- package/dist/bin/deployment/modules/DeploymentOrchestrator.js +0 -492
- package/dist/bin/deployment/modules/EnvironmentManager.js +0 -517
- package/dist/bin/deployment/modules/MonitoringIntegration.js +0 -560
- package/dist/bin/deployment/modules/ValidationManager.js +0 -342
- package/dist/bin/deployment/orchestration/BaseDeploymentOrchestrator.js +0 -426
- package/dist/bin/deployment/orchestration/EnterpriseOrchestrator.js +0 -401
- package/dist/bin/deployment/orchestration/PortfolioOrchestrator.js +0 -273
- package/dist/bin/deployment/orchestration/SingleServiceOrchestrator.js +0 -231
- package/dist/bin/deployment/orchestration/UnifiedDeploymentOrchestrator.js +0 -662
- package/dist/bin/deployment/test-interactive-utils.js +0 -66
- package/dist/bin/portfolio/portfolio-manager.js +0 -487
- package/dist/bin/service-management/create-service.js +0 -122
- package/dist/bin/service-management/init-service.js +0 -79
- package/dist/config/customers.js +0 -623
- package/dist/config/domains.js +0 -186
- package/dist/config/index.js +0 -6
- package/dist/database/database-orchestrator.js +0 -795
- package/dist/database/index.js +0 -4
- package/dist/deployment/index.js +0 -11
- package/dist/deployment/orchestration/BaseDeploymentOrchestrator.js +0 -426
- package/dist/deployment/orchestration/EnterpriseOrchestrator.js +0 -401
- package/dist/deployment/orchestration/PortfolioOrchestrator.js +0 -273
- package/dist/deployment/orchestration/SingleServiceOrchestrator.js +0 -231
- package/dist/deployment/orchestration/UnifiedDeploymentOrchestrator.js +0 -662
- package/dist/deployment/orchestration/index.js +0 -17
- package/dist/deployment/rollback-manager.js +0 -36
- package/dist/deployment/wrangler-deployer.js +0 -640
- package/dist/handlers/GenericRouteHandler.js +0 -532
- package/dist/migration/MigrationAdapters.js +0 -562
- package/dist/modules/ModuleManager.js +0 -668
- package/dist/modules/security.js +0 -96
- package/dist/orchestration/cross-domain-coordinator.js +0 -1083
- package/dist/orchestration/index.js +0 -5
- package/dist/orchestration/modules/DeploymentCoordinator.js +0 -368
- package/dist/orchestration/modules/DomainResolver.js +0 -198
- package/dist/orchestration/modules/StateManager.js +0 -332
- package/dist/orchestration/multi-domain-orchestrator.js +0 -724
- package/dist/routing/EnhancedRouter.js +0 -158
- package/dist/schema/SchemaManager.js +0 -778
- package/dist/service-management/ConfirmationEngine.js +0 -412
- package/dist/service-management/ErrorTracker.js +0 -299
- package/dist/service-management/GenerationEngine.js +0 -447
- package/dist/service-management/InputCollector.js +0 -619
- package/dist/service-management/ServiceCreator.js +0 -265
- package/dist/service-management/ServiceInitializer.js +0 -453
- package/dist/service-management/ServiceOrchestrator.js +0 -633
- package/dist/service-management/generators/BaseGenerator.js +0 -233
- package/dist/service-management/generators/GeneratorRegistry.js +0 -254
- package/dist/service-management/generators/cicd/CiWorkflowGenerator.js +0 -87
- package/dist/service-management/generators/cicd/DeployWorkflowGenerator.js +0 -106
- package/dist/service-management/generators/code/ServiceHandlersGenerator.js +0 -235
- package/dist/service-management/generators/code/ServiceMiddlewareGenerator.js +0 -116
- package/dist/service-management/generators/code/ServiceUtilsGenerator.js +0 -246
- package/dist/service-management/generators/code/WorkerIndexGenerator.js +0 -143
- package/dist/service-management/generators/config/DevelopmentEnvGenerator.js +0 -101
- package/dist/service-management/generators/config/DomainsConfigGenerator.js +0 -175
- package/dist/service-management/generators/config/EnvExampleGenerator.js +0 -178
- package/dist/service-management/generators/config/ProductionEnvGenerator.js +0 -97
- package/dist/service-management/generators/config/StagingEnvGenerator.js +0 -97
- package/dist/service-management/generators/config/WranglerTomlGenerator.js +0 -238
- package/dist/service-management/generators/core/PackageJsonGenerator.js +0 -243
- package/dist/service-management/generators/core/SiteConfigGenerator.js +0 -115
- package/dist/service-management/generators/documentation/ApiDocsGenerator.js +0 -331
- package/dist/service-management/generators/documentation/ConfigurationDocsGenerator.js +0 -294
- package/dist/service-management/generators/documentation/DeploymentDocsGenerator.js +0 -244
- package/dist/service-management/generators/documentation/ReadmeGenerator.js +0 -196
- package/dist/service-management/generators/schemas/ServiceSchemaGenerator.js +0 -190
- package/dist/service-management/generators/scripts/DeployScriptGenerator.js +0 -123
- package/dist/service-management/generators/scripts/HealthCheckScriptGenerator.js +0 -101
- package/dist/service-management/generators/scripts/SetupScriptGenerator.js +0 -88
- package/dist/service-management/generators/service-types/StaticSiteGenerator.js +0 -342
- package/dist/service-management/generators/testing/EslintConfigGenerator.js +0 -85
- package/dist/service-management/generators/testing/IntegrationTestsGenerator.js +0 -237
- package/dist/service-management/generators/testing/JestConfigGenerator.js +0 -72
- package/dist/service-management/generators/testing/UnitTestsGenerator.js +0 -277
- package/dist/service-management/generators/tooling/DockerComposeGenerator.js +0 -71
- package/dist/service-management/generators/tooling/GitignoreGenerator.js +0 -143
- package/dist/service-management/generators/utils/FileWriter.js +0 -179
- package/dist/service-management/generators/utils/PathResolver.js +0 -157
- package/dist/service-management/generators/utils/ServiceManifestGenerator.js +0 -111
- package/dist/service-management/generators/utils/TemplateEngine.js +0 -185
- package/dist/service-management/generators/utils/index.js +0 -18
- package/dist/service-management/handlers/ConfirmationHandler.js +0 -71
- package/dist/service-management/handlers/GenerationHandler.js +0 -80
- package/dist/service-management/handlers/InputHandler.js +0 -59
- package/dist/service-management/handlers/ValidationHandler.js +0 -203
- package/dist/service-management/index.js +0 -14
- package/dist/service-management/routing/DomainRouteMapper.js +0 -311
- package/dist/service-management/routing/RouteGenerator.js +0 -266
- package/dist/service-management/routing/WranglerRoutesBuilder.js +0 -273
- package/dist/service-management/routing/index.js +0 -14
- package/dist/service-management/services/DirectoryStructureService.js +0 -56
- package/dist/service-management/services/GenerationCoordinator.js +0 -208
- package/dist/service-management/services/GeneratorRegistry.js +0 -174
- package/dist/services/GenericDataService.js +0 -501
- package/dist/ui-structures/concepts/second-order-acquisition-strategy.md +0 -286
- package/dist/ui-structures/concepts/service-lifecycle-management.md +0 -150
- package/dist/ui-structures/concepts/service-manifest-guide.md +0 -309
- package/dist/ui-structures/concepts/three-tier-categorization-strategy.md +0 -231
- package/dist/ui-structures/creation/automated-generation-ui.json +0 -246
- package/dist/ui-structures/creation/core-inputs-ui.json +0 -217
- package/dist/ui-structures/creation/smart-confirmable-ui.json +0 -451
- package/dist/ui-structures/reference/absolutely-required-inputs.json +0 -315
- package/dist/ui-structures/reference/service-manifest-template.json +0 -342
- package/dist/version/VersionDetector.js +0 -723
- package/dist/worker/index.js +0 -4
- package/dist/worker/integration.js +0 -351
|
@@ -1,66 +0,0 @@
|
|
|
1
|
-
#!/usr/bin/env node
|
|
2
|
-
|
|
3
|
-
/**
|
|
4
|
-
* Test Enhanced Interactive Utils
|
|
5
|
-
* Quick test to verify the enhanced interactive base improvements
|
|
6
|
-
*/
|
|
7
|
-
import { askUser, askYesNo, askChoice, DeploymentInteractiveUtils, startProgress, closePrompts } from '../shared/utils/interactive-utils.js';
|
|
8
|
-
async function testEnhancedInteractiveUtils() {
|
|
9
|
-
console.log('🧪 Testing Enhanced Interactive Utils v2.0.0');
|
|
10
|
-
console.log('============================================');
|
|
11
|
-
try {
|
|
12
|
-
// Test progress tracking
|
|
13
|
-
const progressTracker = startProgress(5, 'Starting Interactive Tests');
|
|
14
|
-
|
|
15
|
-
// Test enhanced yes/no with colors
|
|
16
|
-
progressTracker.nextStep('Testing Enhanced Yes/No Prompts');
|
|
17
|
-
const continueTest = await askYesNo('Continue with interactive utils test?', 'y');
|
|
18
|
-
if (!continueTest) {
|
|
19
|
-
console.log('Test cancelled by user');
|
|
20
|
-
return;
|
|
21
|
-
}
|
|
22
|
-
|
|
23
|
-
// Test deployment interactive utilities
|
|
24
|
-
progressTracker.nextStep('Testing Deployment-Specific Utilities');
|
|
25
|
-
const deployUtils = new DeploymentInteractiveUtils({
|
|
26
|
-
enableColors: true,
|
|
27
|
-
enableProgress: true,
|
|
28
|
-
validateInputs: true
|
|
29
|
-
});
|
|
30
|
-
|
|
31
|
-
// Test deployment mode selection
|
|
32
|
-
progressTracker.nextStep('Testing Deployment Mode Selection');
|
|
33
|
-
console.log('\n🎯 Testing Enhanced Deployment Mode Selection:');
|
|
34
|
-
const deploymentMode = await deployUtils.askDeploymentMode(0);
|
|
35
|
-
console.log(`Selected mode: ${deploymentMode}`);
|
|
36
|
-
|
|
37
|
-
// Test domain validation
|
|
38
|
-
progressTracker.nextStep('Testing Domain Validation');
|
|
39
|
-
console.log('\n🌐 Testing Domain Validation:');
|
|
40
|
-
const testDomain = await deployUtils.askDomain('Enter a test domain (e.g., "testcorp")');
|
|
41
|
-
console.log(`Valid domain entered: ${testDomain}`);
|
|
42
|
-
|
|
43
|
-
// Test environment selection with warnings
|
|
44
|
-
progressTracker.nextStep('Testing Environment Selection');
|
|
45
|
-
console.log('\n🌍 Testing Environment Selection with Warnings:');
|
|
46
|
-
const environment = await deployUtils.askEnvironment(2); // Default to development
|
|
47
|
-
console.log(`Selected environment: ${environment}`);
|
|
48
|
-
console.log('\n🎉 Enhanced Interactive Utils Test Completed Successfully!');
|
|
49
|
-
console.log('Features tested:');
|
|
50
|
-
console.log(' ✅ Progress tracking with visual progress bars');
|
|
51
|
-
console.log(' ✅ Enhanced prompts with color formatting');
|
|
52
|
-
console.log(' ✅ Input validation with retry logic');
|
|
53
|
-
console.log(' ✅ Deployment-specific utilities');
|
|
54
|
-
console.log(' ✅ Environment warnings and confirmations');
|
|
55
|
-
} catch (error) {
|
|
56
|
-
console.error(`❌ Test failed: ${error.message}`);
|
|
57
|
-
} finally {
|
|
58
|
-
closePrompts();
|
|
59
|
-
}
|
|
60
|
-
}
|
|
61
|
-
|
|
62
|
-
// Run the test
|
|
63
|
-
if (process.argv[1] && import.meta.url.includes(process.argv[1].replace(/\\\\/g, '/'))) {
|
|
64
|
-
testEnhancedInteractiveUtils().catch(console.error);
|
|
65
|
-
}
|
|
66
|
-
export { testEnhancedInteractiveUtils };
|
|
@@ -1,487 +0,0 @@
|
|
|
1
|
-
#!/usr/bin/env node
|
|
2
|
-
|
|
3
|
-
/**
|
|
4
|
-
* Portfolio Management CLI
|
|
5
|
-
*
|
|
6
|
-
* Comprehensive multi-domain portfolio operations and management system.
|
|
7
|
-
* Advanced bulk operations, health monitoring, and cross-domain coordination.
|
|
8
|
-
*
|
|
9
|
-
* Portfolio Features:
|
|
10
|
-
* - Multi-domain portfolio discovery and management
|
|
11
|
-
* - Bulk deployment operations with dependency resolution
|
|
12
|
-
* - Advanced health monitoring and alerting
|
|
13
|
-
* - Cross-domain secret and configuration synchronization
|
|
14
|
-
* - Portfolio-wide testing and validation
|
|
15
|
-
* - Comprehensive reporting and analytics
|
|
16
|
-
* - Automated maintenance and cleanup operations
|
|
17
|
-
* - Configuration template management
|
|
18
|
-
* - Performance monitoring and optimization
|
|
19
|
-
* - Compliance and security auditing
|
|
20
|
-
*
|
|
21
|
-
* @version 2.0.0 - Enterprise Edition
|
|
22
|
-
*/
|
|
23
|
-
import { program } from 'commander';
|
|
24
|
-
import { existsSync, readFileSync, writeFileSync } from 'fs';
|
|
25
|
-
import { join } from 'path';
|
|
26
|
-
import { createWriteStream } from 'fs';
|
|
27
|
-
|
|
28
|
-
// Enterprise module imports - organized shared modules
|
|
29
|
-
import { CrossDomainCoordinator } from "../../orchestration/cross-domain-coordinator.js";
|
|
30
|
-
import { MultiDomainOrchestrator } from "../../orchestration/multi-domain-orchestrator.js";
|
|
31
|
-
import { DeploymentValidator } from '../shared/deployment/validator.js';
|
|
32
|
-
import { DomainDiscovery } from '../shared/cloudflare/domain-discovery.js';
|
|
33
|
-
import { DatabaseOrchestrator } from "../../database/database-orchestrator.js";
|
|
34
|
-
import { EnhancedSecretManager } from '../shared/security/secret-generator.js';
|
|
35
|
-
import { ConfigurationCacheManager } from '../shared/config/cache.js';
|
|
36
|
-
import { ProductionTester } from '../shared/production-tester/index.js';
|
|
37
|
-
import { DeploymentAuditor } from '../shared/deployment/auditor.js';
|
|
38
|
-
class PortfolioManagerCLI {
|
|
39
|
-
constructor() {
|
|
40
|
-
this.version = '2.0.0';
|
|
41
|
-
this.modules = {};
|
|
42
|
-
this.portfolioConfig = this.loadPortfolioConfig();
|
|
43
|
-
}
|
|
44
|
-
|
|
45
|
-
/**
|
|
46
|
-
* Initialize the CLI asynchronously
|
|
47
|
-
*/
|
|
48
|
-
async initialize() {
|
|
49
|
-
await this.initializeModules();
|
|
50
|
-
this.setupCommands();
|
|
51
|
-
}
|
|
52
|
-
|
|
53
|
-
/**
|
|
54
|
-
* Load portfolio configuration
|
|
55
|
-
*/
|
|
56
|
-
loadPortfolioConfig() {
|
|
57
|
-
const configPath = join(process.cwd(), 'portfolio.config.json');
|
|
58
|
-
if (existsSync(configPath)) {
|
|
59
|
-
try {
|
|
60
|
-
return JSON.parse(readFileSync(configPath, 'utf8'));
|
|
61
|
-
} catch (error) {
|
|
62
|
-
console.warn('⚠️ Failed to load portfolio config, using defaults');
|
|
63
|
-
}
|
|
64
|
-
}
|
|
65
|
-
return {
|
|
66
|
-
name: 'tamyla-portfolio',
|
|
67
|
-
defaultEnvironment: 'production',
|
|
68
|
-
healthCheckInterval: 300000,
|
|
69
|
-
// 5 minutes
|
|
70
|
-
maxConcurrentOperations: 5,
|
|
71
|
-
alertWebhook: null,
|
|
72
|
-
reportingFormats: ['json', 'html', 'csv'],
|
|
73
|
-
backupRetention: 90,
|
|
74
|
-
// days
|
|
75
|
-
autoDiscovery: true,
|
|
76
|
-
crossDomainSecrets: true,
|
|
77
|
-
dependencyResolution: true,
|
|
78
|
-
rollbackThreshold: 0.8
|
|
79
|
-
};
|
|
80
|
-
}
|
|
81
|
-
|
|
82
|
-
/**
|
|
83
|
-
* Initialize enterprise modules
|
|
84
|
-
*/
|
|
85
|
-
async initializeModules() {
|
|
86
|
-
const domainDiscovery = new DomainDiscovery({
|
|
87
|
-
enableCaching: true,
|
|
88
|
-
autoDiscovery: this.portfolioConfig.autoDiscovery
|
|
89
|
-
});
|
|
90
|
-
domainDiscovery.initializeDiscovery();
|
|
91
|
-
this.modules = {
|
|
92
|
-
coordinator: new CrossDomainCoordinator({
|
|
93
|
-
portfolioName: this.portfolioConfig.name
|
|
94
|
-
}),
|
|
95
|
-
orchestrator: new MultiDomainOrchestrator({
|
|
96
|
-
maxConcurrentDeployments: this.portfolioConfig.maxConcurrentOperations
|
|
97
|
-
}),
|
|
98
|
-
validator: new DeploymentValidator({
|
|
99
|
-
validationLevel: 'comprehensive'
|
|
100
|
-
}),
|
|
101
|
-
domainDiscovery,
|
|
102
|
-
databaseOrchestrator: new DatabaseOrchestrator({
|
|
103
|
-
enableSafeMode: true,
|
|
104
|
-
portfolioMode: true
|
|
105
|
-
}),
|
|
106
|
-
secretManager: new EnhancedSecretManager({
|
|
107
|
-
crossDomainCoordination: this.portfolioConfig.crossDomainSecrets
|
|
108
|
-
}),
|
|
109
|
-
productionTester: new ProductionTester({
|
|
110
|
-
comprehensiveTests: true,
|
|
111
|
-
portfolioTesting: true
|
|
112
|
-
}),
|
|
113
|
-
auditor: new DeploymentAuditor({
|
|
114
|
-
auditLevel: 'verbose',
|
|
115
|
-
portfolioAudit: true
|
|
116
|
-
}),
|
|
117
|
-
configCache: new ConfigurationCacheManager({
|
|
118
|
-
enableRuntimeDiscovery: true,
|
|
119
|
-
portfolioTemplates: true
|
|
120
|
-
})
|
|
121
|
-
};
|
|
122
|
-
|
|
123
|
-
// Initialize async components
|
|
124
|
-
await this.modules.configCache.initialize();
|
|
125
|
-
}
|
|
126
|
-
|
|
127
|
-
/**
|
|
128
|
-
* Setup CLI commands
|
|
129
|
-
*/
|
|
130
|
-
setupCommands() {
|
|
131
|
-
program.name('portfolio-manager').description('Portfolio Management System - Comprehensive multi-domain operations').version(this.version);
|
|
132
|
-
|
|
133
|
-
// Portfolio discovery and initialization
|
|
134
|
-
program.command('init').description('Initialize portfolio management system').option('--portfolio-name <name>', 'portfolio name', this.portfolioConfig.name).option('--discover', 'auto-discover domains from Cloudflare').option('--interactive', 'interactive configuration setup').action(options => this.initializePortfolio(options));
|
|
135
|
-
program.command('discover').description('Discover and catalog all domains in portfolio').option('--token <token>', 'Cloudflare API token').option('--update-config', 'update portfolio configuration with discoveries').option('--deep-scan', 'perform deep configuration scanning').option('--cache-results', 'cache discovery results').action(options => this.discoverPortfolio(options));
|
|
136
|
-
|
|
137
|
-
// Portfolio operations
|
|
138
|
-
program.command('deploy').description('Deploy entire portfolio with coordination').option('-e, --env <environment>', 'deployment environment', this.portfolioConfig.defaultEnvironment).option('-f, --filter <pattern>', 'filter domains by regex pattern').option('--exclude <pattern>', 'exclude domains matching pattern').option('-b, --batch-size <size>', 'batch size for parallel deployments', '3').option('--dependency-order', 'resolve and use dependency ordering').option('--health-check', 'run pre-deployment health checks').option('--rollback-threshold <percent>', 'rollback threshold (0-1)', this.portfolioConfig.rollbackThreshold.toString()).option('--dry-run', 'simulate deployment without changes').option('--force', 'force deployment even with validation failures').action(options => this.deployPortfolio(options));
|
|
139
|
-
program.command('validate').description('Validate entire portfolio deployment readiness').option('-e, --env <environment>', 'environment to validate', this.portfolioConfig.defaultEnvironment).option('--cross-domain', 'include cross-domain compatibility checks').option('--dependency-check', 'validate domain dependencies').option('--fix', 'attempt to auto-fix validation issues').option('--report <format>', 'generate validation report (json|html|csv)', 'html').action(options => this.validatePortfolio(options));
|
|
140
|
-
program.command('test').description('Run comprehensive portfolio testing').option('--parallel', 'run tests in parallel across domains').option('--suites <suites>', 'test suites to run', 'health,endpoints,integration,cross-domain').option('--threshold <percent>', 'success threshold (0-1)', '0.9').option('--timeout <ms>', 'test timeout per domain', '60000').option('--report <format>', 'test report format (json|html|junit)', 'html').option('--load-test', 'include load testing').action(options => this.testPortfolio(options));
|
|
141
|
-
|
|
142
|
-
// Health monitoring
|
|
143
|
-
program.command('health').description('Check portfolio health status').option('--detailed', 'show detailed health information').option('--format <format>', 'output format (table|json|yaml)', 'table').option('--alerts', 'check for active alerts').action(options => this.checkHealth(options));
|
|
144
|
-
program.command('monitor').description('Start continuous portfolio monitoring').option('--interval <ms>', 'monitoring interval', this.portfolioConfig.healthCheckInterval.toString()).option('--alert-webhook <url>', 'webhook URL for alerts').option('--dashboard', 'launch monitoring dashboard').option('--log-file <path>', 'log monitoring results to file').action(options => this.startMonitoring(options));
|
|
145
|
-
|
|
146
|
-
// Bulk operations
|
|
147
|
-
program.command('bulk-update').description('Perform bulk updates across portfolio').option('--operation <operation>', 'update operation (secrets|config|migrations|cleanup)').option('-f, --filter <pattern>', 'filter domains by pattern').option('--exclude <pattern>', 'exclude domains matching pattern').option('--parallel', 'run updates in parallel').option('--dry-run', 'simulate updates without changes').action(options => this.bulkUpdate(options));
|
|
148
|
-
program.command('bulk-secrets').description('Manage secrets across entire portfolio').option('--generate', 'generate new secrets for all domains').option('--rotate <keys>', 'rotate specific secret keys (comma-separated)').option('--sync', 'synchronize shared secrets across domains').option('--deploy', 'deploy secrets to Cloudflare').option('-e, --env <environment>', 'target environment', this.portfolioConfig.defaultEnvironment).action(options => this.bulkSecrets(options));
|
|
149
|
-
program.command('bulk-config').description('Manage configuration across portfolio').option('--template <name>', 'apply configuration template').option('--sync', 'synchronize common configuration').option('--validate', 'validate configuration consistency').option('--backup', 'backup current configurations').action(options => this.bulkConfig(options));
|
|
150
|
-
|
|
151
|
-
// Database operations
|
|
152
|
-
program.command('db-migrate').description('Run database migrations across portfolio').option('-e, --env <environment>', 'target environment', this.portfolioConfig.defaultEnvironment).option('--parallel', 'run migrations in parallel').option('--safe-mode', 'enable extra safety checks').option('--dry-run', 'show migrations without executing').option('--rollback', 'rollback migrations').action(options => this.databaseMigrate(options));
|
|
153
|
-
program.command('db-sync').description('Synchronize database schemas across portfolio').option('-e, --env <environment>', 'source environment', this.portfolioConfig.defaultEnvironment).option('--target-env <env>', 'target environment for sync').option('--schema-only', 'sync schema only, not data').option('--force', 'force sync even with conflicts').action(options => this.databaseSync(options));
|
|
154
|
-
|
|
155
|
-
// Analytics and reporting
|
|
156
|
-
program.command('analytics').description('Generate portfolio analytics and insights').option('--period <days>', 'analysis period in days', '30').option('--metrics <metrics>', 'metrics to analyze (deployments|health|performance|errors)', 'all').option('--format <format>', 'report format (json|html|csv|dashboard)', 'dashboard').option('--export <path>', 'export analytics to file').action(options => this.generateAnalytics(options));
|
|
157
|
-
program.command('report').description('Generate comprehensive portfolio report').option('--type <type>', 'report type (status|health|compliance|performance)', 'status').option('--format <format>', 'report format (json|html|csv|pdf)', 'html').option('--period <days>', 'reporting period in days', '7').option('--include-trends', 'include trend analysis').action(options => this.generateReport(options));
|
|
158
|
-
|
|
159
|
-
// Maintenance operations
|
|
160
|
-
program.command('cleanup').description('Clean up portfolio deployments and logs').option('--days <days>', 'retention period in days', this.portfolioConfig.backupRetention.toString()).option('--type <type>', 'cleanup type (logs|deployments|backups|all)', 'all').option('--force', 'force cleanup without confirmation').option('--dry-run', 'show what would be cleaned up').action(options => this.cleanupPortfolio(options));
|
|
161
|
-
program.command('backup').description('Create portfolio-wide backups').option('--type <type>', 'backup type (config|database|secrets|all)', 'all').option('--compress', 'compress backup files').option('--encrypt', 'encrypt sensitive backup data').option('--remote', 'store backups remotely').action(options => this.backupPortfolio(options));
|
|
162
|
-
program.command('restore').description('Restore portfolio from backup').option('--backup-id <id>', 'backup ID to restore').option('--type <type>', 'restore type (config|database|secrets|all)', 'all').option('--force', 'force restore without confirmation').action(options => this.restorePortfolio(options));
|
|
163
|
-
|
|
164
|
-
// Information and status
|
|
165
|
-
program.command('list').description('List portfolio domains and their status').option('--format <format>', 'output format (table|json|yaml|csv)', 'table').option('--show-health', 'include health status').option('--show-urls', 'include deployment URLs').option('--filter <pattern>', 'filter domains by pattern').action(options => this.listDomains(options));
|
|
166
|
-
program.command('status [domain]').description('Get detailed status for domain or entire portfolio').option('--detailed', 'show detailed status information').option('--format <format>', 'output format (table|json|yaml)', 'table').option('--history', 'include deployment history').action((domain, options) => this.getStatus(domain, options));
|
|
167
|
-
program.command('dependencies').description('Show domain dependencies and relationships').option('--graph', 'show dependency graph').option('--format <format>', 'output format (text|json|dot)', 'text').option('--resolve-order', 'show deployment order based on dependencies').action(options => this.showDependencies(options));
|
|
168
|
-
|
|
169
|
-
// Configuration management
|
|
170
|
-
program.command('config').description('Manage portfolio configuration').option('--show', 'show current configuration').option('--edit', 'edit configuration interactively').option('--template <name>', 'generate configuration template').option('--validate', 'validate configuration').action(options => this.manageConfig(options));
|
|
171
|
-
|
|
172
|
-
// Global options
|
|
173
|
-
program.option('--verbose', 'verbose output').option('--quiet', 'quiet mode - minimal output').option('--no-color', 'disable colored output').option('--config <file>', 'custom portfolio configuration file');
|
|
174
|
-
|
|
175
|
-
// Parse CLI arguments
|
|
176
|
-
program.parse();
|
|
177
|
-
}
|
|
178
|
-
|
|
179
|
-
/**
|
|
180
|
-
* Initialize portfolio management system
|
|
181
|
-
*/
|
|
182
|
-
async initializePortfolio(options) {
|
|
183
|
-
try {
|
|
184
|
-
this.logOutput(`🚀 Initializing portfolio: ${options.name}`, 'info');
|
|
185
|
-
const portfolioSetup = {
|
|
186
|
-
name: options.name,
|
|
187
|
-
createdAt: new Date().toISOString(),
|
|
188
|
-
version: this.version
|
|
189
|
-
};
|
|
190
|
-
if (options.discover) {
|
|
191
|
-
this.logOutput('🔍 Auto-discovering domains...', 'info');
|
|
192
|
-
const discoveredDomains = await this.modules.coordinator.discoverPortfolio();
|
|
193
|
-
portfolioSetup.domains = discoveredDomains.domains;
|
|
194
|
-
this.logOutput(`✅ Discovered ${discoveredDomains.domains.length} domains`, 'success');
|
|
195
|
-
}
|
|
196
|
-
|
|
197
|
-
// Save portfolio configuration
|
|
198
|
-
const configPath = join(process.cwd(), 'portfolio.config.json');
|
|
199
|
-
writeFileSync(configPath, JSON.stringify(portfolioSetup, null, 2));
|
|
200
|
-
this.logOutput(`✅ Portfolio initialized: ${options.name}`, 'success');
|
|
201
|
-
} catch (error) {
|
|
202
|
-
this.logOutput(`❌ Portfolio initialization failed: ${error.message}`, 'error');
|
|
203
|
-
process.exit(1);
|
|
204
|
-
}
|
|
205
|
-
}
|
|
206
|
-
|
|
207
|
-
/**
|
|
208
|
-
* Discover portfolio domains
|
|
209
|
-
*/
|
|
210
|
-
async discoverPortfolio(options) {
|
|
211
|
-
try {
|
|
212
|
-
this.logOutput('🔍 Discovering portfolio domains...', 'info');
|
|
213
|
-
const discoveryOptions = {
|
|
214
|
-
cloudflareToken: options.token,
|
|
215
|
-
deepScan: options.deepScan,
|
|
216
|
-
cacheResults: options.cacheResults,
|
|
217
|
-
updateConfig: options.updateConfig
|
|
218
|
-
};
|
|
219
|
-
const portfolio = await this.modules.coordinator.discoverPortfolio(discoveryOptions);
|
|
220
|
-
this.logOutput(`✅ Discovered ${portfolio.domains.length} domains`, 'success');
|
|
221
|
-
if (options.updateConfig) {
|
|
222
|
-
const configPath = join(process.cwd(), 'portfolio.config.json');
|
|
223
|
-
const config = this.portfolioConfig;
|
|
224
|
-
config.domains = portfolio.domains;
|
|
225
|
-
config.lastDiscovery = new Date().toISOString();
|
|
226
|
-
writeFileSync(configPath, JSON.stringify(config, null, 2));
|
|
227
|
-
this.logOutput('📝 Updated portfolio configuration', 'info');
|
|
228
|
-
}
|
|
229
|
-
|
|
230
|
-
// Display discovered domains
|
|
231
|
-
console.log('\\n📋 Discovered Domains:');
|
|
232
|
-
portfolio.domains.forEach((domain, index) => {
|
|
233
|
-
console.log(` ${index + 1}. ${domain.name || domain.domain}`);
|
|
234
|
-
if (domain.url) console.log(` 🔗 ${domain.url}`);
|
|
235
|
-
if (domain.environment) console.log(` 🌍 ${domain.environment}`);
|
|
236
|
-
});
|
|
237
|
-
} catch (error) {
|
|
238
|
-
this.logOutput(`❌ Portfolio discovery failed: ${error.message}`, 'error');
|
|
239
|
-
process.exit(1);
|
|
240
|
-
}
|
|
241
|
-
}
|
|
242
|
-
|
|
243
|
-
/**
|
|
244
|
-
* Deploy entire portfolio
|
|
245
|
-
*/
|
|
246
|
-
async deployPortfolio(options) {
|
|
247
|
-
try {
|
|
248
|
-
this.logOutput('🌍 Starting portfolio deployment...', 'info');
|
|
249
|
-
|
|
250
|
-
// Discover portfolio if not cached
|
|
251
|
-
const portfolio = await this.modules.coordinator.discoverPortfolio();
|
|
252
|
-
let domains = portfolio.domains.map(d => d.name || d.domain);
|
|
253
|
-
|
|
254
|
-
// Apply filters
|
|
255
|
-
if (options.filter) {
|
|
256
|
-
const filterRegex = new RegExp(options.filter);
|
|
257
|
-
domains = domains.filter(domain => filterRegex.test(domain));
|
|
258
|
-
}
|
|
259
|
-
if (options.exclude) {
|
|
260
|
-
const excludeRegex = new RegExp(options.exclude);
|
|
261
|
-
domains = domains.filter(domain => !excludeRegex.test(domain));
|
|
262
|
-
}
|
|
263
|
-
this.logOutput(`📊 Deploying ${domains.length} domains`, 'info');
|
|
264
|
-
|
|
265
|
-
// Health check if requested
|
|
266
|
-
if (options.healthCheck) {
|
|
267
|
-
this.logOutput('❤️ Running pre-deployment health checks...', 'info');
|
|
268
|
-
const healthResults = await this.modules.coordinator.monitorPortfolioHealth();
|
|
269
|
-
if (healthResults.summary.unhealthy > 0) {
|
|
270
|
-
this.logOutput(`⚠️ ${healthResults.summary.unhealthy} domains unhealthy`, 'warn');
|
|
271
|
-
if (!options.force) {
|
|
272
|
-
this.logOutput('❌ Aborting deployment due to health issues. Use --force to override.', 'error');
|
|
273
|
-
process.exit(1);
|
|
274
|
-
}
|
|
275
|
-
}
|
|
276
|
-
}
|
|
277
|
-
|
|
278
|
-
// Execute portfolio deployment
|
|
279
|
-
const deploymentOptions = {
|
|
280
|
-
environment: options.env,
|
|
281
|
-
batchSize: parseInt(options.batchSize),
|
|
282
|
-
resolveDependencies: options.dependencyOrder,
|
|
283
|
-
rollbackThreshold: parseFloat(options.rollbackThreshold),
|
|
284
|
-
dryRun: options.dryRun
|
|
285
|
-
};
|
|
286
|
-
const result = await this.modules.coordinator.coordinateMultiDomainDeployment(domains, deploymentOptions);
|
|
287
|
-
this.logOutput('✅ Portfolio deployment completed', 'success');
|
|
288
|
-
console.log(` ✅ Successful: ${result.results.successful.length}`);
|
|
289
|
-
console.log(` ❌ Failed: ${result.results.failed.length}`);
|
|
290
|
-
console.log(` ⏱️ Total Duration: ${result.totalDuration}s`);
|
|
291
|
-
if (result.results.failed.length > 0) {
|
|
292
|
-
console.log('\\n❌ Failed Deployments:');
|
|
293
|
-
result.results.failed.forEach(failure => {
|
|
294
|
-
console.log(` - ${failure.domain}: ${failure.error}`);
|
|
295
|
-
});
|
|
296
|
-
}
|
|
297
|
-
} catch (error) {
|
|
298
|
-
this.logOutput(`❌ Portfolio deployment failed: ${error.message}`, 'error');
|
|
299
|
-
process.exit(1);
|
|
300
|
-
}
|
|
301
|
-
}
|
|
302
|
-
|
|
303
|
-
/**
|
|
304
|
-
* Check portfolio health
|
|
305
|
-
*/
|
|
306
|
-
async checkHealth(options) {
|
|
307
|
-
try {
|
|
308
|
-
this.logOutput('❤️ Checking portfolio health...', 'info');
|
|
309
|
-
const healthResults = await this.modules.coordinator.monitorPortfolioHealth();
|
|
310
|
-
this.logOutput('✅ Health check completed', 'success');
|
|
311
|
-
if (options.format === 'table') {
|
|
312
|
-
console.log('\\n📊 Portfolio Health Summary:');
|
|
313
|
-
console.log(` 📊 Total Domains: ${healthResults.summary.total}`);
|
|
314
|
-
console.log(` ✅ Healthy: ${healthResults.summary.healthy}`);
|
|
315
|
-
console.log(` ⚠️ Warnings: ${healthResults.summary.warnings || 0}`);
|
|
316
|
-
console.log(` ❌ Unhealthy: ${healthResults.summary.unhealthy}`);
|
|
317
|
-
console.log(` 🔥 Errors: ${healthResults.summary.errors}`);
|
|
318
|
-
if (options.detailed) {
|
|
319
|
-
console.log('\\n📋 Domain Details:');
|
|
320
|
-
healthResults.domains.forEach(domain => {
|
|
321
|
-
const status = domain.healthy ? '✅' : '❌';
|
|
322
|
-
console.log(` ${status} ${domain.domain}`);
|
|
323
|
-
if (domain.issues?.length > 0) {
|
|
324
|
-
domain.issues.forEach(issue => console.log(` - ${issue}`));
|
|
325
|
-
}
|
|
326
|
-
});
|
|
327
|
-
}
|
|
328
|
-
} else {
|
|
329
|
-
console.log(JSON.stringify(healthResults, null, 2));
|
|
330
|
-
}
|
|
331
|
-
} catch (error) {
|
|
332
|
-
this.logOutput(`❌ Health check failed: ${error.message}`, 'error');
|
|
333
|
-
process.exit(1);
|
|
334
|
-
}
|
|
335
|
-
}
|
|
336
|
-
|
|
337
|
-
/**
|
|
338
|
-
* Start continuous monitoring
|
|
339
|
-
*/
|
|
340
|
-
async startMonitoring(options) {
|
|
341
|
-
try {
|
|
342
|
-
this.logOutput('📊 Starting portfolio monitoring...', 'info');
|
|
343
|
-
const interval = parseInt(options.interval);
|
|
344
|
-
let logStream = null;
|
|
345
|
-
if (options.logFile) {
|
|
346
|
-
logStream = createWriteStream(options.logFile, {
|
|
347
|
-
flags: 'a'
|
|
348
|
-
});
|
|
349
|
-
}
|
|
350
|
-
const runHealthCheck = async () => {
|
|
351
|
-
const timestamp = new Date().toISOString();
|
|
352
|
-
const healthResults = await this.modules.coordinator.monitorPortfolioHealth();
|
|
353
|
-
const summary = `[${timestamp}] Health: ${healthResults.summary.healthy}/${healthResults.summary.total} healthy`;
|
|
354
|
-
this.logOutput(summary, 'info');
|
|
355
|
-
if (logStream) {
|
|
356
|
-
logStream.write(summary + '\\n');
|
|
357
|
-
}
|
|
358
|
-
|
|
359
|
-
// Send alerts if configured and issues detected
|
|
360
|
-
if (options.alertWebhook && healthResults.summary.unhealthy > 0) {
|
|
361
|
-
this.logOutput(`🚨 Alert: ${healthResults.summary.unhealthy} domains unhealthy`, 'warn');
|
|
362
|
-
// Implementation would send HTTP POST to webhook
|
|
363
|
-
}
|
|
364
|
-
};
|
|
365
|
-
|
|
366
|
-
// Initial check
|
|
367
|
-
await runHealthCheck();
|
|
368
|
-
|
|
369
|
-
// Continuous monitoring
|
|
370
|
-
const monitoringInterval = setInterval(runHealthCheck, interval);
|
|
371
|
-
this.logOutput(`🔄 Continuous monitoring started (interval: ${interval}ms)`, 'info');
|
|
372
|
-
this.logOutput('Press Ctrl+C to stop monitoring', 'info');
|
|
373
|
-
|
|
374
|
-
// Graceful shutdown
|
|
375
|
-
process.on('SIGINT', () => {
|
|
376
|
-
clearInterval(monitoringInterval);
|
|
377
|
-
if (logStream) logStream.end();
|
|
378
|
-
this.logOutput('\\n⏹️ Monitoring stopped', 'info');
|
|
379
|
-
process.exit(0);
|
|
380
|
-
});
|
|
381
|
-
} catch (error) {
|
|
382
|
-
this.logOutput(`❌ Monitoring failed: ${error.message}`, 'error');
|
|
383
|
-
process.exit(1);
|
|
384
|
-
}
|
|
385
|
-
}
|
|
386
|
-
|
|
387
|
-
/**
|
|
388
|
-
* Generate deployment ID
|
|
389
|
-
*/
|
|
390
|
-
generateDeploymentId() {
|
|
391
|
-
const timestamp = Date.now().toString(36);
|
|
392
|
-
const random = Math.random().toString(36).substr(2, 9);
|
|
393
|
-
return `portfolio_${timestamp}_${random}`;
|
|
394
|
-
}
|
|
395
|
-
|
|
396
|
-
/**
|
|
397
|
-
* Log output with different levels
|
|
398
|
-
*/
|
|
399
|
-
logOutput(message, level = 'info') {
|
|
400
|
-
if (program.opts().quiet && level !== 'error') return;
|
|
401
|
-
const colors = {
|
|
402
|
-
info: '\\x1b[36m',
|
|
403
|
-
// Cyan
|
|
404
|
-
success: '\\x1b[32m',
|
|
405
|
-
// Green
|
|
406
|
-
warn: '\\x1b[33m',
|
|
407
|
-
// Yellow
|
|
408
|
-
error: '\\x1b[31m',
|
|
409
|
-
// Red
|
|
410
|
-
reset: '\\x1b[0m' // Reset
|
|
411
|
-
};
|
|
412
|
-
const useColor = !program.opts().noColor;
|
|
413
|
-
const colorCode = useColor ? colors[level] || colors.info : '';
|
|
414
|
-
const resetCode = useColor ? colors.reset : '';
|
|
415
|
-
console.log(`${colorCode}${message}${resetCode}`);
|
|
416
|
-
}
|
|
417
|
-
|
|
418
|
-
/**
|
|
419
|
-
* Placeholder implementations for remaining methods
|
|
420
|
-
*/
|
|
421
|
-
async validatePortfolio(options) {
|
|
422
|
-
this.logOutput('🔍 Portfolio validation not yet implemented', 'warn');
|
|
423
|
-
}
|
|
424
|
-
async testPortfolio(options) {
|
|
425
|
-
this.logOutput('🧪 Portfolio testing not yet implemented', 'warn');
|
|
426
|
-
}
|
|
427
|
-
async bulkUpdate(options) {
|
|
428
|
-
this.logOutput(`🔄 Bulk ${options.operation} update not yet implemented`, 'warn');
|
|
429
|
-
}
|
|
430
|
-
async bulkSecrets(options) {
|
|
431
|
-
this.logOutput('🔐 Bulk secret management not yet implemented', 'warn');
|
|
432
|
-
}
|
|
433
|
-
async bulkConfig(options) {
|
|
434
|
-
this.logOutput('⚙️ Bulk configuration management not yet implemented', 'warn');
|
|
435
|
-
}
|
|
436
|
-
async databaseMigrate(options) {
|
|
437
|
-
this.logOutput('🗄️ Portfolio database migration not yet implemented', 'warn');
|
|
438
|
-
}
|
|
439
|
-
async databaseSync(options) {
|
|
440
|
-
this.logOutput('🔄 Database synchronization not yet implemented', 'warn');
|
|
441
|
-
}
|
|
442
|
-
async generateAnalytics(options) {
|
|
443
|
-
this.logOutput('📊 Analytics generation not yet implemented', 'warn');
|
|
444
|
-
}
|
|
445
|
-
async generateReport(options) {
|
|
446
|
-
this.logOutput(`📋 ${options.type} report generation not yet implemented`, 'warn');
|
|
447
|
-
}
|
|
448
|
-
async cleanupPortfolio(options) {
|
|
449
|
-
this.logOutput(`🧹 Portfolio ${options.type} cleanup not yet implemented`, 'warn');
|
|
450
|
-
}
|
|
451
|
-
async backupPortfolio(options) {
|
|
452
|
-
this.logOutput(`💾 Portfolio ${options.type} backup not yet implemented`, 'warn');
|
|
453
|
-
}
|
|
454
|
-
async restorePortfolio(options) {
|
|
455
|
-
this.logOutput(`🔄 Portfolio ${options.type} restore not yet implemented`, 'warn');
|
|
456
|
-
}
|
|
457
|
-
async listDomains(options) {
|
|
458
|
-
this.logOutput('📋 Domain listing not yet implemented', 'warn');
|
|
459
|
-
}
|
|
460
|
-
async getStatus(domain, options) {
|
|
461
|
-
this.logOutput(`📊 Status for ${domain || 'portfolio'} not yet implemented`, 'warn');
|
|
462
|
-
}
|
|
463
|
-
async showDependencies(options) {
|
|
464
|
-
this.logOutput('🔗 Dependency analysis not yet implemented', 'warn');
|
|
465
|
-
}
|
|
466
|
-
async manageConfig(options) {
|
|
467
|
-
this.logOutput('⚙️ Configuration management not yet implemented', 'warn');
|
|
468
|
-
}
|
|
469
|
-
}
|
|
470
|
-
|
|
471
|
-
// Initialize and run CLI
|
|
472
|
-
const cli = new PortfolioManagerCLI();
|
|
473
|
-
cli.initialize().catch(error => {
|
|
474
|
-
console.error('❌ Failed to initialize CLI:', error.message);
|
|
475
|
-
process.exit(1);
|
|
476
|
-
});
|
|
477
|
-
|
|
478
|
-
// Handle unhandled errors
|
|
479
|
-
process.on('uncaughtException', error => {
|
|
480
|
-
console.error('❌ Uncaught Exception:', error.message);
|
|
481
|
-
process.exit(1);
|
|
482
|
-
});
|
|
483
|
-
process.on('unhandledRejection', (reason, promise) => {
|
|
484
|
-
console.error('❌ Unhandled Rejection at:', promise, 'reason:', reason);
|
|
485
|
-
process.exit(1);
|
|
486
|
-
});
|
|
487
|
-
export { PortfolioManagerCLI };
|
|
@@ -1,122 +0,0 @@
|
|
|
1
|
-
#!/usr/bin/env node
|
|
2
|
-
|
|
3
|
-
/**
|
|
4
|
-
* Clodo Framework - Service Template Generator
|
|
5
|
-
* Creates new ser console.log(`✓ Using Clodo Framework ServiceCreator module`);ices from predefined templates
|
|
6
|
-
*/
|
|
7
|
-
import { ServiceCreator } from "../../service-management/ServiceCreator.js";
|
|
8
|
-
const SERVICE_TYPES = ['data-service', 'auth-service', 'content-service', 'api-gateway', 'generic'];
|
|
9
|
-
function showUsage() {
|
|
10
|
-
console.log(`
|
|
11
|
-
Clodo Framework - Service Template Generator
|
|
12
|
-
|
|
13
|
-
Usage: clodo-create-service <service-name> [options]
|
|
14
|
-
|
|
15
|
-
Arguments:
|
|
16
|
-
service-name Name of the service to create (required)
|
|
17
|
-
|
|
18
|
-
Options:
|
|
19
|
-
-t, --type <type> Service type: ${SERVICE_TYPES.join(', ')} (default: generic)
|
|
20
|
-
-o, --output <path> Output directory (default: current directory)
|
|
21
|
-
-f, --force Overwrite existing service directory
|
|
22
|
-
-h, --help Show this help message
|
|
23
|
-
|
|
24
|
-
Examples:
|
|
25
|
-
clodo-create-service my-data-service --type data-service
|
|
26
|
-
clodo-create-service auth-api --type auth-service --output ./services
|
|
27
|
-
clodo-create-service my-service --force
|
|
28
|
-
`);
|
|
29
|
-
}
|
|
30
|
-
function parseArgs(args) {
|
|
31
|
-
const options = {
|
|
32
|
-
type: 'generic',
|
|
33
|
-
output: process.cwd(),
|
|
34
|
-
force: false
|
|
35
|
-
};
|
|
36
|
-
let serviceName = null;
|
|
37
|
-
for (let i = 0; i < args.length; i++) {
|
|
38
|
-
const arg = args[i];
|
|
39
|
-
switch (arg) {
|
|
40
|
-
case '-t':
|
|
41
|
-
case '--type':
|
|
42
|
-
options.type = args[++i];
|
|
43
|
-
break;
|
|
44
|
-
case '-o':
|
|
45
|
-
case '--output':
|
|
46
|
-
options.output = args[++i];
|
|
47
|
-
break;
|
|
48
|
-
case '-f':
|
|
49
|
-
case '--force':
|
|
50
|
-
options.force = true;
|
|
51
|
-
break;
|
|
52
|
-
case '-h':
|
|
53
|
-
case '--help':
|
|
54
|
-
showUsage();
|
|
55
|
-
process.exit(0);
|
|
56
|
-
break;
|
|
57
|
-
default:
|
|
58
|
-
if (!arg.startsWith('-') && !serviceName) {
|
|
59
|
-
serviceName = arg;
|
|
60
|
-
} else {
|
|
61
|
-
console.error(`Unknown option: ${arg}`);
|
|
62
|
-
showUsage();
|
|
63
|
-
process.exit(1);
|
|
64
|
-
}
|
|
65
|
-
}
|
|
66
|
-
}
|
|
67
|
-
if (!serviceName) {
|
|
68
|
-
console.error('Error: Service name is required');
|
|
69
|
-
showUsage();
|
|
70
|
-
process.exit(1);
|
|
71
|
-
}
|
|
72
|
-
if (!SERVICE_TYPES.includes(options.type)) {
|
|
73
|
-
console.error(`Error: Invalid service type. Must be one of: ${SERVICE_TYPES.join(', ')}`);
|
|
74
|
-
process.exit(1);
|
|
75
|
-
}
|
|
76
|
-
return {
|
|
77
|
-
serviceName,
|
|
78
|
-
options
|
|
79
|
-
};
|
|
80
|
-
}
|
|
81
|
-
|
|
82
|
-
// Main execution
|
|
83
|
-
async function main() {
|
|
84
|
-
try {
|
|
85
|
-
const args = process.argv.slice(2);
|
|
86
|
-
const {
|
|
87
|
-
serviceName,
|
|
88
|
-
options
|
|
89
|
-
} = parseArgs(args);
|
|
90
|
-
console.log(`🚀 Creating ${options.type} service: ${serviceName}`);
|
|
91
|
-
console.log(`✓ Using Clodo Framework ServiceCreator module`);
|
|
92
|
-
console.log('');
|
|
93
|
-
const creator = new ServiceCreator();
|
|
94
|
-
const result = await creator.createService(serviceName, options);
|
|
95
|
-
if (result.success) {
|
|
96
|
-
console.log('✅ Service created successfully!');
|
|
97
|
-
console.log('');
|
|
98
|
-
console.log('📝 Next steps:');
|
|
99
|
-
console.log(` cd ${result.serviceDir.split('/').pop() || result.serviceDir.split('\\').pop()}`);
|
|
100
|
-
console.log(' npm install');
|
|
101
|
-
console.log(' npm run setup # Configure domain and Cloudflare settings');
|
|
102
|
-
console.log(' npm run dev # Start development server');
|
|
103
|
-
console.log('');
|
|
104
|
-
console.log('📚 Documentation:');
|
|
105
|
-
console.log(' README.md # Service documentation');
|
|
106
|
-
console.log(' API.md # API documentation');
|
|
107
|
-
console.log('');
|
|
108
|
-
console.log('🔗 Useful commands:');
|
|
109
|
-
console.log(' npm test # Run tests');
|
|
110
|
-
console.log(' npm run deploy # Deploy to Cloudflare');
|
|
111
|
-
} else {
|
|
112
|
-
console.error('❌ Service creation failed:', result.error);
|
|
113
|
-
process.exit(1);
|
|
114
|
-
}
|
|
115
|
-
} catch (error) {
|
|
116
|
-
console.error('❌ Unexpected error:', error.message);
|
|
117
|
-
process.exit(1);
|
|
118
|
-
}
|
|
119
|
-
}
|
|
120
|
-
|
|
121
|
-
// Run the generator
|
|
122
|
-
main();
|