@geek-fun/serverlessinsight 0.6.15 → 0.7.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 (44) hide show
  1. package/AGENTS.md +405 -10
  2. package/README.md +1 -0
  3. package/dist/package.json +8 -2
  4. package/dist/src/commands/deploy.js +4 -0
  5. package/dist/src/commands/destroy.js +4 -0
  6. package/dist/src/common/credentials.js +12 -0
  7. package/dist/src/common/providerEnum.js +1 -0
  8. package/dist/src/common/runtimeMapper.js +24 -3
  9. package/dist/src/common/volcengineClient/apigwOperations.js +271 -0
  10. package/dist/src/common/volcengineClient/iamOperations.js +349 -0
  11. package/dist/src/common/volcengineClient/index.js +99 -0
  12. package/dist/src/common/volcengineClient/tlsOperations.js +256 -0
  13. package/dist/src/common/volcengineClient/tosOperations.js +440 -0
  14. package/dist/src/common/volcengineClient/types.js +26 -0
  15. package/dist/src/common/volcengineClient/vefaasOperations.js +386 -0
  16. package/dist/src/lang/en.js +120 -0
  17. package/dist/src/lang/zh-CN.js +119 -0
  18. package/dist/src/stack/deploy.js +4 -0
  19. package/dist/src/stack/volcengineStack/apigwExecutor.js +87 -0
  20. package/dist/src/stack/volcengineStack/apigwPlanner.js +110 -0
  21. package/dist/src/stack/volcengineStack/apigwResource.js +302 -0
  22. package/dist/src/stack/volcengineStack/apigwTypes.js +106 -0
  23. package/dist/src/stack/volcengineStack/deployer.js +59 -0
  24. package/dist/src/stack/volcengineStack/destroyer.js +72 -0
  25. package/dist/src/stack/volcengineStack/index.js +44 -0
  26. package/dist/src/stack/volcengineStack/planner.js +27 -0
  27. package/dist/src/stack/volcengineStack/tosExecutor.js +106 -0
  28. package/dist/src/stack/volcengineStack/tosPlanner.js +96 -0
  29. package/dist/src/stack/volcengineStack/tosResource.js +103 -0
  30. package/dist/src/stack/volcengineStack/tosTypes.js +65 -0
  31. package/dist/src/stack/volcengineStack/vefaasExecutor.js +102 -0
  32. package/dist/src/stack/volcengineStack/vefaasPlanner.js +84 -0
  33. package/dist/src/stack/volcengineStack/vefaasResource.js +513 -0
  34. package/dist/src/stack/volcengineStack/vefaasTypes.js +75 -0
  35. package/dist/src/types/domains/state.js +3 -0
  36. package/dist/src/validator/functionSchema.js +13 -0
  37. package/dist/src/validator/rootSchema.js +1 -1
  38. package/dist/tsconfig.tsbuildinfo +1 -1
  39. package/package.json +8 -2
  40. package/samples/volcengine-poc-advanced.yml +59 -0
  41. package/samples/volcengine-poc-api.yml +31 -0
  42. package/samples/volcengine-poc-bucket.yml +17 -0
  43. package/samples/volcengine-poc-function.yml +19 -0
  44. package/samples/volcengine-poc-vpc.yml +34 -0
package/AGENTS.md CHANGED
@@ -247,22 +247,99 @@ logger.error(lang.__('FAILED_TO_DEPLOY_STACK', { error }));
247
247
 
248
248
  ### Testing
249
249
 
250
- - Tests live in `tests/` mirroring the `src/` structure
251
- - Use Jest with `jest.fn()` for mocks
252
- - Group mocks at the top of the test file
253
- - Use `jest.mock()` for module mocking before imports
254
- - Use `describe/it` blocks for organization
250
+ **Test Folder Structure**:
251
+
252
+ ```
253
+ tests/
254
+ ├── fixtures/ # Test fixtures (YAML configs, artifacts)
255
+ ├── unit/ # Unit tests (end with .test.ts)
256
+ │ ├── common/
257
+ │ ├── stack/
258
+ │ └── ...
259
+ └── service/ # Service tests (end with .spec.test.ts)
260
+ └── ...
261
+ ```
262
+
263
+ **Test Commands**:
264
+
265
+ ```bash
266
+ # Run all tests
267
+ npm test
268
+
269
+ # Run unit tests only
270
+ npm run test:unit
271
+
272
+ # Run service tests only
273
+ npm run test:service
274
+
275
+ # Run CI tests
276
+ npm run test:ci
277
+ ```
278
+
279
+ **Unit Tests** (`.test.ts`):
280
+
281
+ - Test individual functions/modules in complete isolation
282
+ - Mock ALL external dependencies (SDK clients, file system, network)
283
+ - Focus on business logic and edge cases
284
+ - Run fast (< 100ms per test)
285
+ - Located in `tests/unit/`
286
+
287
+ **Service Tests** (`.spec.test.ts`):
288
+
289
+ - Test the complete flow from command entry to final result
290
+ - Mock ONLY external cloud SDK clients
291
+ - Test framework internals: parser → planner → executor → state
292
+ - Verify component interaction and state consistency
293
+ - Run slower (1-10s per test)
294
+ - Located in `tests/service/`
295
+
296
+ **When to Write Which Test**:
297
+
298
+ | Scenario | Unit Test | Service Test |
299
+ | ----------------------------------- | --------- | ------------ |
300
+ | New utility function | ✅ | ❌ |
301
+ | New SDK operation wrapper | ✅ | ❌ |
302
+ | New resource planner | ✅ | ❌ |
303
+ | Deploy command flow | ❌ | ✅ |
304
+ | State persistence across operations | ❌ | ✅ |
305
+ | Error handling in full flow | ❌ | ✅ |
306
+
307
+ **Mock Strategy**:
308
+
309
+ ```typescript
310
+ // Unit Test: Mock everything external
311
+ jest.mock('../../../../src/common/aliyunClient', () => ({
312
+ createAliyunClient: jest.fn(() => ({
313
+ fc3: { createFunction: jest.fn() },
314
+ })),
315
+ }));
316
+
317
+ // Service Test: Mock only cloud SDK
318
+ const mockCloudClient = {
319
+ fc3: { createFunction: jest.fn() },
320
+ apigw: { createApi: jest.fn() },
321
+ };
322
+ // Use real parser, real planner, real executor
323
+ ```
324
+
325
+ **CRITICAL: Test Coverage Requirements**
326
+
327
+ - Coverage threshold is set to **85%** for all metrics (branches, functions, lines, statements)
328
+ - **NEVER modify the coverage threshold** in `jest.config.js`
329
+ - If tests fail due to coverage, add more tests - do not lower the threshold
330
+ - This is a mandatory quality gate for the framework
331
+
332
+ **Unit Test Example**:
255
333
 
256
334
  ```typescript
257
335
  describe('updateResource', () => {
258
336
  it('should update resource and refresh state from provider', async () => {
259
- // Arrange
260
- mockedFc3Operations.updateFunctionConfiguration.mockResolvedValue(undefined);
337
+ const mockedFc3Operations = {
338
+ updateFunctionConfiguration: jest.fn(),
339
+ };
261
340
 
262
- // Act
263
- const result = await updateResource(mockContext, testFunction, initialState);
341
+ await updateResource(mockContext, testFunction, initialState);
264
342
 
265
- // Assert
266
343
  expect(mockedFc3Operations.updateFunctionConfiguration).toHaveBeenCalledWith(
267
344
  expect.objectContaining({ functionName: 'test-function' }),
268
345
  );
@@ -270,6 +347,284 @@ describe('updateResource', () => {
270
347
  });
271
348
  ```
272
349
 
350
+ **Service Test Example**:
351
+
352
+ ```typescript
353
+ describe('Deploy Flow', () => {
354
+ it('should parse YAML, generate plan, execute, and save state', async () => {
355
+ const mockClient = createMockAliyunClient();
356
+ const config = loadTestConfig('fixtures/deploy-fixtures/oneFc');
357
+
358
+ await deployCommand({ config, client: mockClient });
359
+
360
+ expect(mockClient.fc3.createFunction).toHaveBeenCalled();
361
+ const state = await loadState(config.app, config.service);
362
+ expect(state.resources).toHaveLength(1);
363
+ });
364
+ });
365
+ ```
366
+
367
+ ## Test Architecture & Rules (CRITICAL)
368
+
369
+ ### Test Pyramid
370
+
371
+ ```
372
+ /\
373
+ / \
374
+ / E2E \ (Future: Full integration tests)
375
+ /--------\
376
+ / Service \ (Integration-style, mock ONLY cloud SDKs)
377
+ /------------\
378
+ / Unit \ (Isolated, mock ALL externals)
379
+ /----------------\
380
+ ```
381
+
382
+ ### Unit Test Rules (`.test.ts`)
383
+
384
+ **Purpose**: Test individual functions/modules in complete isolation
385
+
386
+ **DO**:
387
+
388
+ - Mock ALL external dependencies (SDK clients, file system, network, logger)
389
+ - Test pure business logic
390
+ - Use inline `jest.mock()` for dependencies
391
+ - Keep tests fast (< 100ms)
392
+ - Test edge cases and error handling
393
+ - Use descriptive test names that explain the scenario
394
+
395
+ **DON'T**:
396
+
397
+ - Import real cloud SDKs
398
+ - Access real file system
399
+ - Make network calls
400
+ - Test multiple functions together
401
+ - Rely on external state
402
+
403
+ **Example**:
404
+
405
+ ```typescript
406
+ // tests/unit/common/aliyunClient/fc3Operations.test.ts
407
+ import { createFc3Operations } from '../../../../src/common/aliyunClient/fc3Operations';
408
+
409
+ jest.mock('../../../../src/common/logger', () => ({
410
+ logger: { info: jest.fn(), warn: jest.fn(), error: jest.fn() },
411
+ }));
412
+
413
+ jest.mock('../../../../src/lang', () => ({
414
+ lang: { __: (key: string) => key },
415
+ }));
416
+
417
+ const mockFc3SdkClient = {
418
+ createFunction: jest.fn(),
419
+ getFunction: jest.fn(),
420
+ deleteFunction: jest.fn(),
421
+ };
422
+
423
+ describe('createFc3Operations', () => {
424
+ let operations: ReturnType<typeof createFc3Operations>;
425
+
426
+ beforeEach(() => {
427
+ operations = createFc3Operations(mockFc3SdkClient as any);
428
+ jest.clearAllMocks();
429
+ });
430
+
431
+ it('should create function successfully', async () => {
432
+ mockFc3SdkClient.createFunction.mockResolvedValue({ body: { functionName: 'test-fn' } });
433
+
434
+ const result = await operations.createFunction({ functionName: 'test-fn' }, 'base64code');
435
+
436
+ expect(result).toEqual({ functionName: 'test-fn' });
437
+ expect(mockFc3SdkClient.createFunction).toHaveBeenCalledWith(
438
+ expect.objectContaining({ functionName: 'test-fn' }),
439
+ 'base64code',
440
+ );
441
+ });
442
+ });
443
+ ```
444
+
445
+ ### Service Test Rules (`.spec.test.ts`)
446
+
447
+ **Purpose**: Test complete flows from command entry to final result
448
+
449
+ **DO**:
450
+
451
+ - Mock ONLY external cloud SDK clients via `createMockAliyunClient()` / `createMockTencentClient()`
452
+ - Use REAL internal modules (parser, planner, executor, state manager, lock manager)
453
+ - Use REAL fixture files from `tests/fixtures/`
454
+ - Test end-to-end scenarios
455
+ - Verify state persistence and component interactions
456
+ - Use `jest.mock()` at the top level for SDK modules only
457
+
458
+ **DON'T**:
459
+
460
+ - Mock internal modules (parser, planner, executor, stateManager, lockManager, etc.)
461
+ - Mock file system operations (use real fixtures)
462
+ - Mock logger (service tests can log)
463
+ - Mock hashUtils or other utilities
464
+ - Override `jest.requireActual()` - let internal code run normally
465
+
466
+ **CRITICAL**: Service tests are integration tests. They verify that all internal components work together correctly. Over-mocking defeats their purpose.
467
+
468
+ **Example**:
469
+
470
+ ```typescript
471
+ // tests/service/deploy-flow.spec.test.ts
472
+ import { deploy } from '../../src/commands/deploy';
473
+ import { createMockAliyunClient } from './mockCloudClient';
474
+
475
+ // ONLY mock external SDK
476
+ jest.mock('../../src/common/aliyunClient', () => ({
477
+ createAliyunClient: jest.fn(),
478
+ }));
479
+
480
+ jest.mock('../../src/common/imsClient', () => ({
481
+ getIamInfo: jest.fn().mockResolvedValue({
482
+ accountId: '123456789012',
483
+ displayName: 'Test User',
484
+ userId: 'test-user-id',
485
+ }),
486
+ }));
487
+
488
+ jest.mock('../../src/common/logger', () => ({
489
+ logger: { info: jest.fn(), warn: jest.fn(), error: jest.fn(), debug: jest.fn() },
490
+ }));
491
+
492
+ jest.mock('../../src/lang', () => ({
493
+ lang: { __: (key: string) => key },
494
+ }));
495
+
496
+ const mockCreateAliyunClient = require('../../src/common/aliyunClient').createAliyunClient;
497
+
498
+ describe('Deploy Flow Service Test', () => {
499
+ let mockClient: ReturnType<typeof createMockAliyunClient>;
500
+
501
+ beforeEach(() => {
502
+ jest.clearAllMocks();
503
+ mockClient = createMockAliyunClient();
504
+ mockCreateAliyunClient.mockReturnValue(mockClient);
505
+ });
506
+
507
+ it('should deploy FC3 function and save state', async () => {
508
+ // Use REAL fixtures, REAL parser, REAL planner, REAL executor
509
+ await deploy({
510
+ location: path.join(__dirname, '../fixtures'),
511
+ stage: 'dev',
512
+ autoApprove: true,
513
+ region: 'cn-hangzhou',
514
+ provider: 'aliyun',
515
+ });
516
+
517
+ // Verify cloud SDK was called correctly
518
+ expect(mockClient.fc3.createFunction).toHaveBeenCalled();
519
+ });
520
+ });
521
+ ```
522
+
523
+ ### Mock Cloud Client Pattern
524
+
525
+ **Location**: `tests/service/mockCloudClient.ts`
526
+
527
+ All service tests should use the shared mock cloud client:
528
+
529
+ ```typescript
530
+ // Create mock client with all services
531
+ const mockClient = createMockAliyunClient();
532
+
533
+ // Configure specific behavior per test
534
+ mockClient.fc3.getFunction.mockRejectedValueOnce({ code: 'FunctionNotFound' });
535
+ mockClient.fc3.createFunction.mockResolvedValue({ body: { functionName: 'test-fn' } });
536
+
537
+ // Return from mocked createAliyunClient
538
+ mockCreateAliyunClient.mockReturnValue(mockClient);
539
+ ```
540
+
541
+ **Services to Mock**:
542
+
543
+ - `fc3` - Function Compute
544
+ - `apigw` - API Gateway
545
+ - `oss` - Object Storage Service
546
+ - `sls` - Log Service
547
+ - `ram` - Resource Access Management
548
+ - `nas` - Network Attached Storage
549
+ - `rds` - Relational Database Service
550
+ - `ecs` - Elastic Compute Service
551
+ - `es` - Elasticsearch Serverless
552
+ - `dns` - DNS (for domain operations)
553
+ - `cas` - Certificate Authority Service
554
+
555
+ ### Common Mistakes to Avoid
556
+
557
+ **WRONG - Over-mocking in service tests**:
558
+
559
+ ```typescript
560
+ // DON'T DO THIS in service tests
561
+ jest.mock('../../src/parser', () => ({
562
+ parseYaml: jest.fn(() => ({
563
+ /* mock data */
564
+ })),
565
+ }));
566
+
567
+ jest.mock('../../src/common/stateManager', () => ({
568
+ getResource: jest.fn(),
569
+ setResource: jest.fn(),
570
+ }));
571
+
572
+ jest.mock('../../src/common/lockManager', () => ({
573
+ withLock: jest.fn(),
574
+ }));
575
+ ```
576
+
577
+ **CORRECT - Only mock external SDKs**:
578
+
579
+ ```typescript
580
+ // DO THIS - only mock cloud SDK
581
+ jest.mock('../../src/common/aliyunClient', () => ({
582
+ createAliyunClient: jest.fn(),
583
+ }));
584
+
585
+ jest.mock('../../src/common/imsClient', () => ({
586
+ getIamInfo: jest.fn().mockResolvedValue({
587
+ /* IAM data */
588
+ }),
589
+ }));
590
+ ```
591
+
592
+ ### Test File Naming
593
+
594
+ - **Unit tests**: `*.test.ts` (e.g., `fc3Resource.test.ts`)
595
+ - **Service tests**: `*.spec.test.ts` (e.g., `deploy-flow.spec.test.ts`)
596
+ - **Fixtures**: `tests/fixtures/` (YAML configs, artifacts, state files)
597
+
598
+ ### Running Tests
599
+
600
+ ```bash
601
+ # All tests
602
+ npm test
603
+
604
+ # Unit tests only (fast, isolated)
605
+ npm run test:unit
606
+
607
+ # Service tests only (slower, integration)
608
+ npm run test:service
609
+
610
+ # CI mode (no coverage, faster)
611
+ npm run test:ci
612
+
613
+ # Specific test file
614
+ npm test -- tests/unit/common/aliyunClient/fc3Operations.test.ts
615
+
616
+ # Test name pattern
617
+ npm test -- --testNamePattern="should create function"
618
+ ```
619
+
620
+ ### Coverage Requirements
621
+
622
+ - **Minimum 85%** for all metrics (branches, functions, lines, statements)
623
+ - **NEVER lower the threshold** in `jest.config.js`
624
+ - If coverage fails, add more tests
625
+ - Unit tests should cover edge cases
626
+ - Service tests should cover full flows
627
+
273
628
  ## Formatting
274
629
 
275
630
  Prettier configuration (`.prettierrc`):
@@ -370,3 +725,43 @@ export const createRamOperations = (ramClient: RamSdkClient) => ({
370
725
  - State is stored in `.serverlessinsight/state-{app}-{service}.json`
371
726
  - Use `setResource`, `getResource`, `removeResource` from `src/common/stateManager`
372
727
  - Resources have a `status`: `'ready'` | `'tainted'`
728
+
729
+ ## Commit Policy - CRITICAL
730
+
731
+ **NEVER commit changes unless the user explicitly requests it.**
732
+
733
+ - Do NOT commit after implementing features
734
+ - Do NOT commit after fixing bugs
735
+ - Do NOT commit after refactoring
736
+ - Do NOT commit for "cleanliness" or "convenience"
737
+ - Wait for explicit user instruction like "commit the changes" or "create a commit"
738
+
739
+ **Rationale**: Users may want to:
740
+
741
+ - Review changes before committing
742
+ - Combine multiple changes into one commit
743
+ - Split changes into different commits
744
+ - Test changes before committing
745
+ - Discard changes without polluting git history
746
+
747
+ **If you accidentally commit**: Immediately revert and apologize.
748
+
749
+ ## Commit Policy - CRITICAL
750
+
751
+ **NEVER commit changes unless the user explicitly requests it.**
752
+
753
+ - Do NOT commit after implementing features
754
+ - Do NOT commit after fixing bugs
755
+ - Do NOT commit after refactoring
756
+ - Do NOT commit for "cleanliness" or "convenience"
757
+ - Wait for explicit user instruction like "commit the changes" or "create a commit"
758
+
759
+ **Rationale**: Users may want to:
760
+
761
+ - Review changes before committing
762
+ - Combine multiple changes into one commit
763
+ - Split changes into different commits
764
+ - Test changes before committing
765
+ - Discard changes without polluting git history
766
+
767
+ **If you accidentally commit**: Immediately revert and apologize.
package/README.md CHANGED
@@ -52,6 +52,7 @@ ServerlessInsight supports the following cloud providers:
52
52
  | ----------------- | ---------------- | -------------- | -------------- | ---------------- | ------- |
53
53
  | **Alibaba Cloud** | ✅ FC3 | ✅ API Gateway | ✅ OSS | ✅ RDS, OTS, ESS | Stable |
54
54
  | **Tencent Cloud** | ✅ SCF | 🚧 Coming Soon | ✅ COS | ✅ TDSQL-C | Stable |
55
+ | **Volcengine** | ✅ veFaaS | ✅ API Gateway | ✅ TOS | — | Stable |
55
56
  | **Huawei Cloud** | ✅ FunctionGraph | 🚧 Coming Soon | 🚧 Coming Soon | 🚧 Coming Soon | Beta |
56
57
  | **AWS** | 🔜 Planned | 🔜 Planned | 🔜 Planned | 🔜 Planned | Planned |
57
58
  | **Azure** | 🔜 Planned | 🔜 Planned | 🔜 Planned | 🔜 Planned | Planned |
package/dist/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@geek-fun/serverlessinsight",
3
- "version": "0.6.15",
3
+ "version": "0.7.0",
4
4
  "description": "Full life cycle cross providers serverless application management for your fast-growing business.",
5
5
  "homepage": "https://serverlessinsight.geekfun.club",
6
6
  "main": "dist/src/index.js",
@@ -10,7 +10,9 @@
10
10
  },
11
11
  "scripts": {
12
12
  "test": "cross-env DEBUG=ServerlessInsight jest --runInBand --detectOpenHandles --coverage --coverageReporters json-summary text html lcov",
13
- "test:ci": "jest --runInBand --ci --coverage --coverageReporters json-summary text html lcov",
13
+ "test:unit": "cross-env DEBUG=ServerlessInsight jest --runInBand --detectOpenHandles --testPathPattern=unit",
14
+ "test:service": "cross-env DEBUG=ServerlessInsight TEST_TYPE=service jest --runInBand --detectOpenHandles --testPathPattern=service",
15
+ "test:ci": "cross-env NODE_OPTIONS=\"--max-old-space-size=8192\" jest --runInBand --ci --coverage --coverageReporters json-summary text html lcov",
14
16
  "build": "tsc --build",
15
17
  "lint:fix": "eslint --fix ./",
16
18
  "lint:check": "eslint ./",
@@ -35,6 +37,7 @@
35
37
  "tencent-cloud-functions",
36
38
  "alibaba-cloud-functions",
37
39
  "huawei-cloud-functions",
40
+ "volcengine-cloud-functions",
38
41
  "serverless-framework",
39
42
  "serverless-management",
40
43
  "serverless-automation",
@@ -46,6 +49,7 @@
46
49
  "azure",
47
50
  "huawei",
48
51
  "google",
52
+ "volcengine",
49
53
  "function"
50
54
  ],
51
55
  "dependencies": {
@@ -61,6 +65,8 @@
61
65
  "@alicloud/ram20150501": "^1.2.0",
62
66
  "@alicloud/rds20140815": "^15.5.1",
63
67
  "@alicloud/sls20201230": "^5.9.0",
68
+ "@volcengine/openapi": "^1.36.0",
69
+ "@volcengine/tos-sdk": "^2.7.0",
64
70
  "ajv": "^8.18.0",
65
71
  "ali-oss": "^6.23.0",
66
72
  "commander": "^14.0.3",
@@ -41,6 +41,7 @@ const stateBackend_1 = require("../common/stateBackend");
41
41
  const parser_1 = require("../parser");
42
42
  const scfStack_1 = require("../stack/scfStack");
43
43
  const aliyunStack_1 = require("../stack/aliyunStack");
44
+ const volcengineStack_1 = require("../stack/volcengineStack");
44
45
  const lang_1 = require("../lang");
45
46
  const askConfirmation = async () => {
46
47
  if (!process.stdin.isTTY) {
@@ -82,6 +83,9 @@ const deploy = async (options) => {
82
83
  else if (iac.provider.name === common_1.ProviderEnum.ALIYUN) {
83
84
  planResult = await (0, aliyunStack_1.generateAliyunPlan)(iac, backend);
84
85
  }
86
+ else if (iac.provider.name === common_1.ProviderEnum.VOLCENGINE) {
87
+ planResult = await (0, volcengineStack_1.generateVolcenginePlan)(iac, backend);
88
+ }
85
89
  else {
86
90
  throw new Error(lang_1.lang.__('PLAN_COMMAND_NOT_SUPPORTED'));
87
91
  }
@@ -7,6 +7,7 @@ const parser_1 = require("../parser");
7
7
  const lang_1 = require("../lang");
8
8
  const scfStack_1 = require("../stack/scfStack");
9
9
  const aliyunStack_1 = require("../stack/aliyunStack");
10
+ const volcengineStack_1 = require("../stack/volcengineStack");
10
11
  const destroyStack = async (options) => {
11
12
  const iacLocation = (0, common_1.getIacLocation)(options.location);
12
13
  const rawIac = (0, parser_1.parseYaml)(iacLocation);
@@ -33,6 +34,9 @@ const destroyStack = async (options) => {
33
34
  else if (iac.provider.name === common_1.ProviderEnum.ALIYUN) {
34
35
  await (0, aliyunStack_1.destroyAliyunStack)(backend);
35
36
  }
37
+ else if (iac.provider.name === common_1.ProviderEnum.VOLCENGINE) {
38
+ await (0, volcengineStack_1.destroyVolcengineStack)(backend);
39
+ }
36
40
  else {
37
41
  throw new Error(`Unsupported provider: ${iac.provider.name}`);
38
42
  }
@@ -11,6 +11,18 @@ const getCredentials = (config, provider) => {
11
11
  };
12
12
  }
13
13
  switch (provider) {
14
+ case providerEnum_1.ProviderEnum.VOLCENGINE:
15
+ return {
16
+ accessKeyId: config?.accessKeyId ??
17
+ process.env.VOLCSTACK_ACCESS_KEY_ID ??
18
+ process.env.VOLCENGINE_ACCESS_KEY_ID,
19
+ accessKeySecret: config?.accessKeySecret ??
20
+ process.env.VOLCSTACK_SECRET_ACCESS_KEY ??
21
+ process.env.VOLCENGINE_ACCESS_KEY_SECRET,
22
+ securityToken: config?.securityToken ??
23
+ process.env.VOLCSTACK_SESSION_TOKEN ??
24
+ process.env.VOLCENGINE_SESSION_TOKEN,
25
+ };
14
26
  case providerEnum_1.ProviderEnum.TENCENT:
15
27
  return {
16
28
  accessKeyId: config?.accessKeyId ?? process.env.TENCENTCLOUD_SECRET_ID,
@@ -7,4 +7,5 @@ var ProviderEnum;
7
7
  ProviderEnum["ALIYUN"] = "aliyun";
8
8
  ProviderEnum["TENCENT"] = "tencent";
9
9
  ProviderEnum["AWS"] = "aws";
10
+ ProviderEnum["VOLCENGINE"] = "volcengine";
10
11
  })(ProviderEnum || (exports.ProviderEnum = ProviderEnum = {}));
@@ -144,14 +144,35 @@ const mapRuntime = (standardRuntime, provider) => {
144
144
  return providerRuntime;
145
145
  };
146
146
  exports.mapRuntime = mapRuntime;
147
- const isRuntimeSupported = (standardRuntime, provider) => {
148
- const mapping = runtimeMappings[standardRuntime];
147
+ const VOLCENGINE_NATIVE_RUNTIMES = [
148
+ 'nodejs/v20',
149
+ 'nodejs/v18',
150
+ 'nodejs/v16',
151
+ 'nodejs/v14',
152
+ 'python/v3.12',
153
+ 'python/v3.11',
154
+ 'python/v3.10',
155
+ 'python/v3.9',
156
+ 'golang/v1',
157
+ 'java/v21',
158
+ 'java/v17',
159
+ 'java/v11',
160
+ 'java/v8',
161
+ ];
162
+ const isRuntimeSupported = (runtime, provider) => {
163
+ if (provider === providerEnum_1.ProviderEnum.VOLCENGINE) {
164
+ return VOLCENGINE_NATIVE_RUNTIMES.includes(runtime);
165
+ }
166
+ const mapping = runtimeMappings[runtime];
149
167
  return !!mapping && !!mapping[provider];
150
168
  };
151
169
  exports.isRuntimeSupported = isRuntimeSupported;
152
170
  const getSupportedRuntimes = (provider) => {
153
171
  if (!provider) {
154
- return Object.values(StandardRuntime);
172
+ return [...Object.values(StandardRuntime), ...VOLCENGINE_NATIVE_RUNTIMES];
173
+ }
174
+ if (provider === providerEnum_1.ProviderEnum.VOLCENGINE) {
175
+ return VOLCENGINE_NATIVE_RUNTIMES;
155
176
  }
156
177
  return Object.entries(runtimeMappings)
157
178
  .filter(([, mapping]) => !!mapping[provider])