@tamyla/clodo-framework 1.0.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 (130) hide show
  1. package/CHANGELOG.md +564 -0
  2. package/LICENSE +21 -0
  3. package/README.md +1393 -0
  4. package/bin/README.md +71 -0
  5. package/bin/clodo-service.js +416 -0
  6. package/bin/security/security-cli.js +96 -0
  7. package/bin/service-management/README.md +74 -0
  8. package/bin/service-management/create-service.js +129 -0
  9. package/bin/service-management/init-service.js +102 -0
  10. package/bin/service-management/init-service.js.backup +889 -0
  11. package/bin/shared/config/customer-cli.js +293 -0
  12. package/dist/config/ConfigurationManager.js +159 -0
  13. package/dist/config/CustomerConfigCLI.js +220 -0
  14. package/dist/config/FeatureManager.js +426 -0
  15. package/dist/config/customers.js +441 -0
  16. package/dist/config/domains.js +180 -0
  17. package/dist/config/features.js +225 -0
  18. package/dist/config/index.js +6 -0
  19. package/dist/database/database-orchestrator.js +730 -0
  20. package/dist/database/index.js +4 -0
  21. package/dist/deployment/auditor.js +971 -0
  22. package/dist/deployment/index.js +10 -0
  23. package/dist/deployment/rollback-manager.js +523 -0
  24. package/dist/deployment/testers/api-tester.js +80 -0
  25. package/dist/deployment/testers/auth-tester.js +129 -0
  26. package/dist/deployment/testers/core.js +217 -0
  27. package/dist/deployment/testers/database-tester.js +105 -0
  28. package/dist/deployment/testers/index.js +74 -0
  29. package/dist/deployment/testers/load-tester.js +120 -0
  30. package/dist/deployment/testers/performance-tester.js +105 -0
  31. package/dist/deployment/validator.js +558 -0
  32. package/dist/deployment/wrangler-deployer.js +574 -0
  33. package/dist/handlers/GenericRouteHandler.js +532 -0
  34. package/dist/index.js +39 -0
  35. package/dist/migration/MigrationAdapters.js +562 -0
  36. package/dist/modules/ModuleManager.js +668 -0
  37. package/dist/modules/security.js +98 -0
  38. package/dist/orchestration/cross-domain-coordinator.js +1083 -0
  39. package/dist/orchestration/index.js +5 -0
  40. package/dist/orchestration/modules/DeploymentCoordinator.js +258 -0
  41. package/dist/orchestration/modules/DomainResolver.js +196 -0
  42. package/dist/orchestration/modules/StateManager.js +332 -0
  43. package/dist/orchestration/multi-domain-orchestrator.js +255 -0
  44. package/dist/routing/EnhancedRouter.js +158 -0
  45. package/dist/schema/SchemaManager.js +778 -0
  46. package/dist/security/ConfigurationValidator.js +490 -0
  47. package/dist/security/DeploymentManager.js +208 -0
  48. package/dist/security/SecretGenerator.js +142 -0
  49. package/dist/security/SecurityCLI.js +228 -0
  50. package/dist/security/index.js +51 -0
  51. package/dist/security/patterns/environment-rules.js +66 -0
  52. package/dist/security/patterns/insecure-patterns.js +21 -0
  53. package/dist/service-management/ConfirmationEngine.js +411 -0
  54. package/dist/service-management/ErrorTracker.js +294 -0
  55. package/dist/service-management/GenerationEngine.js +3109 -0
  56. package/dist/service-management/InputCollector.js +237 -0
  57. package/dist/service-management/ServiceCreator.js +229 -0
  58. package/dist/service-management/ServiceInitializer.js +448 -0
  59. package/dist/service-management/ServiceOrchestrator.js +638 -0
  60. package/dist/service-management/handlers/ConfigMutator.js +130 -0
  61. package/dist/service-management/handlers/ConfirmationHandler.js +71 -0
  62. package/dist/service-management/handlers/GenerationHandler.js +80 -0
  63. package/dist/service-management/handlers/InputHandler.js +59 -0
  64. package/dist/service-management/handlers/ValidationHandler.js +203 -0
  65. package/dist/service-management/index.js +7 -0
  66. package/dist/services/GenericDataService.js +488 -0
  67. package/dist/shared/cloudflare/domain-discovery.js +562 -0
  68. package/dist/shared/cloudflare/domain-manager.js +912 -0
  69. package/dist/shared/cloudflare/index.js +8 -0
  70. package/dist/shared/cloudflare/ops.js +387 -0
  71. package/dist/shared/config/cache.js +1167 -0
  72. package/dist/shared/config/command-config-manager.js +174 -0
  73. package/dist/shared/config/customer-cli.js +258 -0
  74. package/dist/shared/config/index.js +9 -0
  75. package/dist/shared/config/manager.js +289 -0
  76. package/dist/shared/database/connection-manager.js +338 -0
  77. package/dist/shared/database/index.js +7 -0
  78. package/dist/shared/database/orchestrator.js +632 -0
  79. package/dist/shared/deployment/auditor.js +971 -0
  80. package/dist/shared/deployment/index.js +10 -0
  81. package/dist/shared/deployment/rollback-manager.js +523 -0
  82. package/dist/shared/deployment/validator.js +558 -0
  83. package/dist/shared/index.js +32 -0
  84. package/dist/shared/monitoring/health-checker.js +250 -0
  85. package/dist/shared/monitoring/index.js +8 -0
  86. package/dist/shared/monitoring/memory-manager.js +382 -0
  87. package/dist/shared/monitoring/production-monitor.js +390 -0
  88. package/dist/shared/production-tester/api-tester.js +80 -0
  89. package/dist/shared/production-tester/auth-tester.js +129 -0
  90. package/dist/shared/production-tester/core.js +217 -0
  91. package/dist/shared/production-tester/database-tester.js +105 -0
  92. package/dist/shared/production-tester/index.js +74 -0
  93. package/dist/shared/production-tester/load-tester.js +120 -0
  94. package/dist/shared/production-tester/performance-tester.js +105 -0
  95. package/dist/shared/security/api-token-manager.js +296 -0
  96. package/dist/shared/security/index.js +8 -0
  97. package/dist/shared/security/secret-generator.js +918 -0
  98. package/dist/shared/security/secure-token-manager.js +379 -0
  99. package/dist/shared/utils/error-recovery.js +240 -0
  100. package/dist/shared/utils/graceful-shutdown-manager.js +380 -0
  101. package/dist/shared/utils/index.js +9 -0
  102. package/dist/shared/utils/interactive-prompts.js +134 -0
  103. package/dist/shared/utils/rate-limiter.js +249 -0
  104. package/dist/utils/ErrorHandler.js +173 -0
  105. package/dist/utils/deployment/config-cache.js +1160 -0
  106. package/dist/utils/deployment/index.js +6 -0
  107. package/dist/utils/deployment/interactive-prompts.js +97 -0
  108. package/dist/utils/deployment/secret-generator.js +896 -0
  109. package/dist/utils/dirname-helper.js +35 -0
  110. package/dist/utils/domain-config.js +159 -0
  111. package/dist/utils/error-recovery.js +240 -0
  112. package/dist/utils/esm-helper.js +52 -0
  113. package/dist/utils/framework-config.js +481 -0
  114. package/dist/utils/graceful-shutdown-manager.js +379 -0
  115. package/dist/utils/health-checker.js +114 -0
  116. package/dist/utils/index.js +36 -0
  117. package/dist/utils/prompt-handler.js +98 -0
  118. package/dist/utils/usage-tracker.js +252 -0
  119. package/dist/utils/validation.js +112 -0
  120. package/dist/version/VersionDetector.js +723 -0
  121. package/dist/worker/index.js +4 -0
  122. package/dist/worker/integration.js +332 -0
  123. package/docs/FRAMEWORK-ARCHITECTURE-OVERVIEW.md +206 -0
  124. package/docs/INTEGRATION_GUIDE.md +2045 -0
  125. package/docs/README.md +82 -0
  126. package/docs/SECURITY.md +242 -0
  127. package/docs/deployment/deployment-guide.md +540 -0
  128. package/docs/overview.md +280 -0
  129. package/package.json +176 -0
  130. package/types/index.d.ts +575 -0
@@ -0,0 +1,296 @@
1
+ /**
2
+ * API Token Manager
3
+ * Secure management of external service API tokens (Cloudflare, etc.)
4
+ *
5
+ * Features:
6
+ * - Secure token storage with encryption
7
+ * - Interactive token collection
8
+ * - Token validation and testing
9
+ * - Automatic token refresh and management
10
+ */
11
+
12
+ import { readFileSync, writeFileSync, existsSync, mkdirSync } from 'fs';
13
+ import { join, dirname } from 'path';
14
+ import { createHash, createCipheriv, createDecipheriv, randomBytes } from 'crypto';
15
+ import { askUser, askPassword } from '../utils/interactive-prompts.js';
16
+ import { fileURLToPath } from 'url';
17
+ const __filename = fileURLToPath(import.meta.url);
18
+ const __dirname = dirname(__filename);
19
+ export class ApiTokenManager {
20
+ constructor(options = {}) {
21
+ this.projectRoot = options.projectRoot || join(__dirname, '..', '..');
22
+ this.configPath = join(this.projectRoot, '.config-cache', 'api-tokens.json');
23
+ this.encryptionKey = this.getOrCreateEncryptionKey();
24
+
25
+ // Ensure config directory exists
26
+ this.ensureDirectory(dirname(this.configPath));
27
+
28
+ // Load existing tokens
29
+ this.tokens = this.loadTokens();
30
+ console.log('šŸ”‘ API Token Manager initialized');
31
+ console.log(`šŸ“ Config: ${this.configPath}`);
32
+ console.log(`šŸ” Encrypted storage: ${this.isEncrypted() ? 'Yes' : 'No'}`);
33
+ }
34
+
35
+ /**
36
+ * Get or create encryption key for secure token storage
37
+ */
38
+ getOrCreateEncryptionKey() {
39
+ const keyPath = join(this.projectRoot, '.config-cache', '.token-key');
40
+ if (existsSync(keyPath)) {
41
+ return readFileSync(keyPath, 'utf-8').trim();
42
+ }
43
+
44
+ // Generate new encryption key
45
+ const key = randomBytes(32).toString('hex');
46
+ this.ensureDirectory(dirname(keyPath));
47
+ writeFileSync(keyPath, key, {
48
+ mode: 0o600
49
+ }); // Secure file permissions
50
+
51
+ return key;
52
+ }
53
+
54
+ /**
55
+ * Load tokens from encrypted storage
56
+ */
57
+ loadTokens() {
58
+ if (!existsSync(this.configPath)) {
59
+ return {};
60
+ }
61
+ try {
62
+ const data = readFileSync(this.configPath, 'utf-8');
63
+ const config = JSON.parse(data);
64
+
65
+ // Decrypt tokens if they're encrypted
66
+ if (config.encrypted) {
67
+ const decryptedTokens = {};
68
+ for (const [service, encryptedToken] of Object.entries(config.tokens)) {
69
+ try {
70
+ decryptedTokens[service] = this.decryptToken(encryptedToken);
71
+ } catch (error) {
72
+ console.warn(`āš ļø Failed to decrypt token for ${service}`);
73
+ }
74
+ }
75
+ return decryptedTokens;
76
+ }
77
+ return config.tokens || {};
78
+ } catch (error) {
79
+ console.warn('āš ļø Failed to load API tokens, starting fresh');
80
+ return {};
81
+ }
82
+ }
83
+
84
+ /**
85
+ * Save tokens to encrypted storage
86
+ */
87
+ saveTokens() {
88
+ try {
89
+ const encryptedTokens = {};
90
+
91
+ // Encrypt each token
92
+ for (const [service, token] of Object.entries(this.tokens)) {
93
+ encryptedTokens[service] = this.encryptToken(token);
94
+ }
95
+ const config = {
96
+ encrypted: true,
97
+ lastUpdated: new Date().toISOString(),
98
+ services: Object.keys(this.tokens),
99
+ tokens: encryptedTokens
100
+ };
101
+ writeFileSync(this.configPath, JSON.stringify(config, null, 2), {
102
+ mode: 0o600
103
+ });
104
+ console.log(`āœ… API tokens saved securely to ${this.configPath}`);
105
+ } catch (error) {
106
+ console.error('āŒ Failed to save API tokens:', error.message);
107
+ throw error;
108
+ }
109
+ }
110
+
111
+ /**
112
+ * Encrypt token for secure storage
113
+ */
114
+ encryptToken(token) {
115
+ try {
116
+ const algorithm = 'aes-256-cbc';
117
+ const iv = randomBytes(16);
118
+ const cipher = createCipheriv(algorithm, Buffer.from(this.encryptionKey, 'hex'), iv);
119
+ let encrypted = cipher.update(token, 'utf8', 'hex');
120
+ encrypted += cipher.final('hex');
121
+ return iv.toString('hex') + ':' + encrypted;
122
+ } catch (error) {
123
+ console.warn('āš ļø Token encryption failed, storing in plain text');
124
+ return token;
125
+ }
126
+ }
127
+
128
+ /**
129
+ * Decrypt token from storage
130
+ */
131
+ decryptToken(encryptedToken) {
132
+ try {
133
+ const algorithm = 'aes-256-cbc';
134
+ const parts = encryptedToken.split(':');
135
+ if (parts.length !== 2) {
136
+ // Old format or plain text, return as is
137
+ return encryptedToken;
138
+ }
139
+ const iv = Buffer.from(parts[0], 'hex');
140
+ const encrypted = parts[1];
141
+ const decipher = createDecipheriv(algorithm, Buffer.from(this.encryptionKey, 'hex'), iv);
142
+ let decrypted = decipher.update(encrypted, 'hex', 'utf8');
143
+ decrypted += decipher.final('utf8');
144
+ return decrypted;
145
+ } catch (error) {
146
+ // If decryption fails, assume it's plain text (backward compatibility)
147
+ return encryptedToken;
148
+ }
149
+ }
150
+
151
+ /**
152
+ * Get API token for a service, prompting if not available
153
+ */
154
+ async getToken(service, options = {}) {
155
+ const serviceName = service.toLowerCase();
156
+
157
+ // Check if token already exists
158
+ if (this.tokens[serviceName]) {
159
+ console.log(`šŸ”‘ Using cached ${service} API token`);
160
+ return this.tokens[serviceName];
161
+ }
162
+
163
+ // Prompt user for token
164
+ console.log(`\\nšŸ”‘ ${service} API Token Required`);
165
+ console.log('═'.repeat(40));
166
+ if (options.description) {
167
+ console.log(`šŸ“‹ ${options.description}`);
168
+ }
169
+ if (options.instructions) {
170
+ console.log('šŸ’” Instructions:');
171
+ options.instructions.forEach(instruction => {
172
+ console.log(` • ${instruction}`);
173
+ });
174
+ }
175
+ const token = await askPassword(`Enter your ${service} API token:`);
176
+ if (!token || token.trim() === '') {
177
+ throw new Error(`${service} API token is required but not provided`);
178
+ }
179
+
180
+ // Validate token if validator provided
181
+ if (options.validator) {
182
+ console.log(`šŸ” Validating ${service} API token...`);
183
+ try {
184
+ const isValid = await options.validator(token.trim());
185
+ if (!isValid) {
186
+ throw new Error(`Invalid ${service} API token`);
187
+ }
188
+ console.log(`āœ… ${service} API token validated successfully`);
189
+ } catch (error) {
190
+ console.error(`āŒ Token validation failed: ${error.message}`);
191
+ throw error;
192
+ }
193
+ }
194
+
195
+ // Store token
196
+ this.tokens[serviceName] = token.trim();
197
+ this.saveTokens();
198
+ console.log(`āœ… ${service} API token saved securely`);
199
+ return this.tokens[serviceName];
200
+ }
201
+
202
+ /**
203
+ * Check if token exists for a service
204
+ */
205
+ hasToken(service) {
206
+ return !!this.tokens[service.toLowerCase()];
207
+ }
208
+
209
+ /**
210
+ * Remove token for a service
211
+ */
212
+ removeToken(service) {
213
+ const serviceName = service.toLowerCase();
214
+ if (this.tokens[serviceName]) {
215
+ delete this.tokens[serviceName];
216
+ this.saveTokens();
217
+ console.log(`šŸ—‘ļø Removed ${service} API token`);
218
+ return true;
219
+ }
220
+ return false;
221
+ }
222
+
223
+ /**
224
+ * List available tokens (without revealing actual values)
225
+ */
226
+ listTokens() {
227
+ const services = Object.keys(this.tokens);
228
+ if (services.length === 0) {
229
+ console.log('šŸ“ No API tokens stored');
230
+ return [];
231
+ }
232
+ console.log('šŸ”‘ Stored API tokens:');
233
+ services.forEach(service => {
234
+ const token = this.tokens[service];
235
+ const preview = token.substring(0, 8) + '...';
236
+ console.log(` • ${service}: ${preview}`);
237
+ });
238
+ return services;
239
+ }
240
+
241
+ /**
242
+ * Utility methods
243
+ */
244
+ isEncrypted() {
245
+ return !!this.encryptionKey;
246
+ }
247
+ ensureDirectory(dirPath) {
248
+ if (!existsSync(dirPath)) {
249
+ mkdirSync(dirPath, {
250
+ recursive: true,
251
+ mode: 0o700
252
+ });
253
+ }
254
+ }
255
+ }
256
+
257
+ /**
258
+ * Cloudflare API Token Manager
259
+ * Specialized manager for Cloudflare API tokens with validation
260
+ */
261
+ export class CloudflareTokenManager extends ApiTokenManager {
262
+ constructor(options = {}) {
263
+ super(options);
264
+ }
265
+
266
+ /**
267
+ * Get Cloudflare API token with validation
268
+ */
269
+ async getCloudflareToken() {
270
+ return this.getToken('cloudflare', {
271
+ description: 'Cloudflare API token is required for domain verification and deployment operations.',
272
+ instructions: ['Go to Cloudflare Dashboard → My Profile → API Tokens', 'Create a token with Zone:Read and Worker:Edit permissions', 'Copy the token (it will only be shown once)'],
273
+ validator: this.validateCloudflareToken.bind(this)
274
+ });
275
+ }
276
+
277
+ /**
278
+ * Validate Cloudflare API token
279
+ */
280
+ async validateCloudflareToken(token) {
281
+ try {
282
+ const response = await fetch('https://api.cloudflare.com/client/v4/user/tokens/verify', {
283
+ headers: {
284
+ 'Authorization': `Bearer ${token}`,
285
+ 'Content-Type': 'application/json'
286
+ }
287
+ });
288
+ const data = await response.json();
289
+ return response.ok && data.success;
290
+ } catch (error) {
291
+ console.warn('āš ļø Token validation failed (network error)');
292
+ return false;
293
+ }
294
+ }
295
+ }
296
+ export default ApiTokenManager;
@@ -0,0 +1,8 @@
1
+ /**
2
+ * Security Module
3
+ * Exports all security and authentication related utilities
4
+ */
5
+
6
+ export { ApiTokenManager } from './api-token-manager.js';
7
+ export { SecureTokenManager } from './secure-token-manager.js';
8
+ export { SecretGenerator } from './secret-generator.js';