@build-astron-co/nimbus 0.4.1 → 0.4.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/CHANGELOG.md +268 -89
- package/README.md +26 -567
- package/dist/src/agent/compaction-agent.js +24 -12
- package/dist/src/agent/context-manager.js +2 -1
- package/dist/src/agent/expand-files.js +2 -1
- package/dist/src/agent/loop.js +71 -33
- package/dist/src/agent/permissions.js +4 -2
- package/dist/src/agent/system-prompt.js +34 -17
- package/dist/src/app.js +1 -1
- package/dist/src/auth/keychain.js +8 -4
- package/dist/src/auth/store.js +70 -107
- package/dist/src/cli/init.js +35 -19
- package/dist/src/cli/run.js +18 -10
- package/dist/src/cli/serve.js +4 -2
- package/dist/src/cli.js +52 -11
- package/dist/src/commands/alias.js +5 -3
- package/dist/src/commands/audit/index.js +2 -1
- package/dist/src/commands/aws-terraform.js +36 -18
- package/dist/src/commands/completions.js +1 -1
- package/dist/src/commands/config.js +3 -2
- package/dist/src/commands/connect-github.js +92 -0
- package/dist/src/commands/cost/index.js +3 -2
- package/dist/src/commands/deploy.js +15 -10
- package/dist/src/commands/doctor.js +9 -6
- package/dist/src/commands/drift/index.js +2 -1
- package/dist/src/commands/export.js +5 -3
- package/dist/src/commands/generate-terraform.js +110 -2
- package/dist/src/commands/import.js +3 -3
- package/dist/src/commands/incident.js +10 -5
- package/dist/src/commands/login.js +8 -93
- package/dist/src/commands/logs.js +16 -8
- package/dist/src/commands/onboarding.js +6 -4
- package/dist/src/commands/pipeline.js +6 -3
- package/dist/src/commands/plugin.js +3 -2
- package/dist/src/commands/profile.js +27 -14
- package/dist/src/commands/questionnaire.js +1 -1
- package/dist/src/commands/rollback.js +3 -2
- package/dist/src/commands/rollout.js +5 -3
- package/dist/src/commands/runbook.js +17 -10
- package/dist/src/commands/schedule.js +10 -5
- package/dist/src/commands/status.js +2 -1
- package/dist/src/commands/team-context.js +12 -7
- package/dist/src/commands/template.js +1 -1
- package/dist/src/commands/tf/index.js +6 -3
- package/dist/src/commands/upgrade.js +5 -3
- package/dist/src/commands/version.js +6 -3
- package/dist/src/commands/watch.js +6 -3
- package/dist/src/compat/sqlite.js +5 -3
- package/dist/src/config/mode-store.js +2 -1
- package/dist/src/config/profiles.js +4 -2
- package/dist/src/config/types.js +2 -1
- package/dist/src/engine/executor.js +8 -4
- package/dist/src/engine/planner.js +9 -5
- package/dist/src/llm/providers/anthropic.js +6 -3
- package/dist/src/llm/providers/ollama.js +1 -1
- package/dist/src/llm/router.js +22 -7
- package/dist/src/nimbus.js +1 -0
- package/dist/src/sessions/manager.js +6 -3
- package/dist/src/sharing/viewer.js +2 -1
- package/dist/src/tools/file-ops.js +1 -2
- package/dist/src/tools/schemas/devops.js +197 -108
- package/dist/src/tools/schemas/standard.js +1 -1
- package/dist/src/ui/App.js +25 -13
- package/dist/src/ui/FileDiffModal.js +22 -11
- package/dist/src/ui/HelpModal.js +2 -1
- package/dist/src/ui/InputBox.js +6 -3
- package/dist/src/ui/MessageList.js +40 -20
- package/dist/src/ui/TerminalPane.js +2 -1
- package/dist/src/ui/ToolCallDisplay.js +12 -6
- package/dist/src/ui/TreePane.js +2 -1
- package/dist/src/ui/ink/index.js +37 -21
- package/dist/src/version.js +1 -1
- package/dist/src/watcher/index.js +8 -4
- package/package.json +3 -5
- package/src/__tests__/alias.test.ts +0 -133
- package/src/__tests__/app.test.ts +0 -76
- package/src/__tests__/audit.test.ts +0 -877
- package/src/__tests__/circuit-breaker.test.ts +0 -116
- package/src/__tests__/cli-run.test.ts +0 -351
- package/src/__tests__/compat-sqlite.test.ts +0 -68
- package/src/__tests__/context-manager.test.ts +0 -632
- package/src/__tests__/context.test.ts +0 -242
- package/src/__tests__/devops-terminal-gaps.test.ts +0 -718
- package/src/__tests__/doctor.test.ts +0 -48
- package/src/__tests__/enterprise.test.ts +0 -401
- package/src/__tests__/export.test.ts +0 -236
- package/src/__tests__/gap-11-18-20.test.ts +0 -958
- package/src/__tests__/generator.test.ts +0 -433
- package/src/__tests__/helm-streaming.test.ts +0 -127
- package/src/__tests__/hooks.test.ts +0 -582
- package/src/__tests__/incident.test.ts +0 -179
- package/src/__tests__/init.test.ts +0 -487
- package/src/__tests__/intent-parser.test.ts +0 -229
- package/src/__tests__/llm-router.test.ts +0 -209
- package/src/__tests__/logs.test.ts +0 -107
- package/src/__tests__/loop-errors.test.ts +0 -244
- package/src/__tests__/lsp.test.ts +0 -293
- package/src/__tests__/modes.test.ts +0 -336
- package/src/__tests__/perf-optimizations.test.ts +0 -847
- package/src/__tests__/permissions.test.ts +0 -338
- package/src/__tests__/pipeline.test.ts +0 -50
- package/src/__tests__/polish-phase3.test.ts +0 -340
- package/src/__tests__/profile.test.ts +0 -237
- package/src/__tests__/rollback.test.ts +0 -83
- package/src/__tests__/runbook.test.ts +0 -219
- package/src/__tests__/schedule.test.ts +0 -206
- package/src/__tests__/serve.test.ts +0 -275
- package/src/__tests__/sessions.test.ts +0 -322
- package/src/__tests__/sharing.test.ts +0 -340
- package/src/__tests__/snapshots.test.ts +0 -581
- package/src/__tests__/standalone-migration.test.ts +0 -199
- package/src/__tests__/state-db.test.ts +0 -334
- package/src/__tests__/status.test.ts +0 -158
- package/src/__tests__/stream-with-tools.test.ts +0 -778
- package/src/__tests__/subagents.test.ts +0 -176
- package/src/__tests__/system-prompt.test.ts +0 -248
- package/src/__tests__/terminal-gap-v2.test.ts +0 -395
- package/src/__tests__/terminal-parity.test.ts +0 -393
- package/src/__tests__/tf-apply.test.ts +0 -187
- package/src/__tests__/tool-converter.test.ts +0 -256
- package/src/__tests__/tool-schemas.test.ts +0 -602
- package/src/__tests__/tools.test.ts +0 -144
- package/src/__tests__/version-json.test.ts +0 -184
- package/src/__tests__/version.test.ts +0 -49
- package/src/__tests__/watch.test.ts +0 -129
- package/src/agent/compaction-agent.ts +0 -266
- package/src/agent/context-manager.ts +0 -499
- package/src/agent/context.ts +0 -427
- package/src/agent/deploy-preview.ts +0 -487
- package/src/agent/expand-files.ts +0 -108
- package/src/agent/index.ts +0 -68
- package/src/agent/loop.ts +0 -1998
- package/src/agent/modes.ts +0 -429
- package/src/agent/permissions.ts +0 -513
- package/src/agent/subagents/base.ts +0 -116
- package/src/agent/subagents/cost.ts +0 -51
- package/src/agent/subagents/explore.ts +0 -42
- package/src/agent/subagents/general.ts +0 -54
- package/src/agent/subagents/index.ts +0 -102
- package/src/agent/subagents/infra.ts +0 -59
- package/src/agent/subagents/security.ts +0 -69
- package/src/agent/system-prompt.ts +0 -990
- package/src/app.ts +0 -180
- package/src/audit/activity-log.ts +0 -290
- package/src/audit/compliance-checker.ts +0 -540
- package/src/audit/cost-tracker.ts +0 -318
- package/src/audit/index.ts +0 -23
- package/src/audit/security-scanner.ts +0 -641
- package/src/auth/guard.ts +0 -75
- package/src/auth/index.ts +0 -56
- package/src/auth/keychain.ts +0 -82
- package/src/auth/oauth.ts +0 -465
- package/src/auth/providers.ts +0 -470
- package/src/auth/sso.ts +0 -113
- package/src/auth/store.ts +0 -505
- package/src/auth/types.ts +0 -187
- package/src/build.ts +0 -141
- package/src/cli/index.ts +0 -16
- package/src/cli/init.ts +0 -1227
- package/src/cli/openapi-spec.ts +0 -356
- package/src/cli/run.ts +0 -628
- package/src/cli/serve-auth.ts +0 -80
- package/src/cli/serve.ts +0 -539
- package/src/cli/web.ts +0 -71
- package/src/cli.ts +0 -1728
- package/src/clients/core-engine-client.ts +0 -227
- package/src/clients/enterprise-client.ts +0 -334
- package/src/clients/generator-client.ts +0 -351
- package/src/clients/git-client.ts +0 -627
- package/src/clients/github-client.ts +0 -410
- package/src/clients/helm-client.ts +0 -504
- package/src/clients/index.ts +0 -80
- package/src/clients/k8s-client.ts +0 -497
- package/src/clients/llm-client.ts +0 -161
- package/src/clients/rest-client.ts +0 -130
- package/src/clients/service-discovery.ts +0 -38
- package/src/clients/terraform-client.ts +0 -482
- package/src/clients/tools-client.ts +0 -1843
- package/src/clients/ws-client.ts +0 -115
- package/src/commands/alias.ts +0 -100
- package/src/commands/analyze/index.ts +0 -352
- package/src/commands/apply/helm.ts +0 -473
- package/src/commands/apply/index.ts +0 -213
- package/src/commands/apply/k8s.ts +0 -454
- package/src/commands/apply/terraform.ts +0 -582
- package/src/commands/ask.ts +0 -167
- package/src/commands/audit/index.ts +0 -357
- package/src/commands/auth-cloud.ts +0 -407
- package/src/commands/auth-list.ts +0 -134
- package/src/commands/auth-profile.ts +0 -121
- package/src/commands/auth-refresh.ts +0 -187
- package/src/commands/auth-status.ts +0 -141
- package/src/commands/aws/ec2.ts +0 -501
- package/src/commands/aws/iam.ts +0 -397
- package/src/commands/aws/index.ts +0 -133
- package/src/commands/aws/lambda.ts +0 -396
- package/src/commands/aws/rds.ts +0 -439
- package/src/commands/aws/s3.ts +0 -439
- package/src/commands/aws/vpc.ts +0 -393
- package/src/commands/aws-discover.ts +0 -542
- package/src/commands/aws-terraform.ts +0 -755
- package/src/commands/azure/aks.ts +0 -376
- package/src/commands/azure/functions.ts +0 -253
- package/src/commands/azure/index.ts +0 -116
- package/src/commands/azure/storage.ts +0 -478
- package/src/commands/azure/vm.ts +0 -355
- package/src/commands/billing/index.ts +0 -256
- package/src/commands/chat.ts +0 -320
- package/src/commands/completions.ts +0 -268
- package/src/commands/config.ts +0 -372
- package/src/commands/cost/cloud-cost-estimator.ts +0 -266
- package/src/commands/cost/estimator.ts +0 -79
- package/src/commands/cost/index.ts +0 -810
- package/src/commands/cost/parsers/terraform.ts +0 -273
- package/src/commands/cost/parsers/types.ts +0 -25
- package/src/commands/cost/pricing/aws.ts +0 -544
- package/src/commands/cost/pricing/azure.ts +0 -499
- package/src/commands/cost/pricing/gcp.ts +0 -396
- package/src/commands/cost/pricing/index.ts +0 -40
- package/src/commands/demo.ts +0 -250
- package/src/commands/deploy.ts +0 -260
- package/src/commands/doctor.ts +0 -1386
- package/src/commands/drift/index.ts +0 -787
- package/src/commands/explain.ts +0 -277
- package/src/commands/export.ts +0 -146
- package/src/commands/feedback.ts +0 -389
- package/src/commands/fix.ts +0 -324
- package/src/commands/fs/index.ts +0 -402
- package/src/commands/gcp/compute.ts +0 -325
- package/src/commands/gcp/functions.ts +0 -271
- package/src/commands/gcp/gke.ts +0 -438
- package/src/commands/gcp/iam.ts +0 -344
- package/src/commands/gcp/index.ts +0 -129
- package/src/commands/gcp/storage.ts +0 -284
- package/src/commands/generate-helm.ts +0 -1249
- package/src/commands/generate-k8s.ts +0 -1508
- package/src/commands/generate-terraform.ts +0 -1202
- package/src/commands/gh/index.ts +0 -863
- package/src/commands/git/index.ts +0 -1343
- package/src/commands/helm/index.ts +0 -1126
- package/src/commands/help.ts +0 -715
- package/src/commands/history.ts +0 -149
- package/src/commands/import.ts +0 -868
- package/src/commands/incident.ts +0 -166
- package/src/commands/index.ts +0 -367
- package/src/commands/init.ts +0 -1051
- package/src/commands/k8s/index.ts +0 -1137
- package/src/commands/login.ts +0 -716
- package/src/commands/logout.ts +0 -83
- package/src/commands/logs.ts +0 -167
- package/src/commands/onboarding.ts +0 -405
- package/src/commands/pipeline.ts +0 -186
- package/src/commands/plan/display.ts +0 -279
- package/src/commands/plan/index.ts +0 -599
- package/src/commands/plugin.ts +0 -398
- package/src/commands/preview.ts +0 -452
- package/src/commands/profile.ts +0 -342
- package/src/commands/questionnaire.ts +0 -1172
- package/src/commands/resume.ts +0 -47
- package/src/commands/rollback.ts +0 -315
- package/src/commands/rollout.ts +0 -88
- package/src/commands/runbook.ts +0 -346
- package/src/commands/schedule.ts +0 -236
- package/src/commands/status.ts +0 -252
- package/src/commands/team/index.ts +0 -346
- package/src/commands/team-context.ts +0 -220
- package/src/commands/template.ts +0 -233
- package/src/commands/tf/index.ts +0 -1093
- package/src/commands/upgrade.ts +0 -607
- package/src/commands/usage/index.ts +0 -134
- package/src/commands/version.ts +0 -174
- package/src/commands/watch.ts +0 -153
- package/src/compat/index.ts +0 -2
- package/src/compat/runtime.ts +0 -12
- package/src/compat/sqlite.ts +0 -177
- package/src/config/index.ts +0 -17
- package/src/config/manager.ts +0 -530
- package/src/config/mode-store.ts +0 -62
- package/src/config/profiles.ts +0 -84
- package/src/config/safety-policy.ts +0 -358
- package/src/config/schema.ts +0 -125
- package/src/config/types.ts +0 -609
- package/src/config/workspace-state.ts +0 -53
- package/src/context/context-db.ts +0 -199
- package/src/demo/index.ts +0 -349
- package/src/demo/scenarios/full-journey.ts +0 -229
- package/src/demo/scenarios/getting-started.ts +0 -127
- package/src/demo/scenarios/helm-release.ts +0 -341
- package/src/demo/scenarios/k8s-deployment.ts +0 -194
- package/src/demo/scenarios/terraform-vpc.ts +0 -170
- package/src/demo/types.ts +0 -92
- package/src/engine/cost-estimator.ts +0 -480
- package/src/engine/diagram-generator.ts +0 -256
- package/src/engine/drift-detector.ts +0 -902
- package/src/engine/executor.ts +0 -1066
- package/src/engine/index.ts +0 -76
- package/src/engine/orchestrator.ts +0 -636
- package/src/engine/planner.ts +0 -787
- package/src/engine/safety.ts +0 -743
- package/src/engine/verifier.ts +0 -770
- package/src/enterprise/audit.ts +0 -348
- package/src/enterprise/auth.ts +0 -270
- package/src/enterprise/billing.ts +0 -822
- package/src/enterprise/index.ts +0 -17
- package/src/enterprise/teams.ts +0 -443
- package/src/generator/best-practices.ts +0 -1608
- package/src/generator/helm.ts +0 -630
- package/src/generator/index.ts +0 -37
- package/src/generator/intent-parser.ts +0 -514
- package/src/generator/kubernetes.ts +0 -976
- package/src/generator/terraform.ts +0 -1875
- package/src/history/index.ts +0 -8
- package/src/history/manager.ts +0 -250
- package/src/history/types.ts +0 -34
- package/src/hooks/config.ts +0 -432
- package/src/hooks/engine.ts +0 -392
- package/src/hooks/index.ts +0 -4
- package/src/llm/auth-bridge.ts +0 -198
- package/src/llm/circuit-breaker.ts +0 -140
- package/src/llm/config-loader.ts +0 -201
- package/src/llm/cost-calculator.ts +0 -171
- package/src/llm/index.ts +0 -8
- package/src/llm/model-aliases.ts +0 -115
- package/src/llm/provider-registry.ts +0 -63
- package/src/llm/providers/anthropic.ts +0 -462
- package/src/llm/providers/bedrock.ts +0 -477
- package/src/llm/providers/google.ts +0 -405
- package/src/llm/providers/ollama.ts +0 -767
- package/src/llm/providers/openai-compatible.ts +0 -340
- package/src/llm/providers/openai.ts +0 -328
- package/src/llm/providers/openrouter.ts +0 -338
- package/src/llm/router.ts +0 -1104
- package/src/llm/types.ts +0 -232
- package/src/lsp/client.ts +0 -298
- package/src/lsp/languages.ts +0 -119
- package/src/lsp/manager.ts +0 -294
- package/src/mcp/client.ts +0 -402
- package/src/mcp/index.ts +0 -5
- package/src/mcp/manager.ts +0 -133
- package/src/nimbus.ts +0 -233
- package/src/plugins/index.ts +0 -27
- package/src/plugins/loader.ts +0 -334
- package/src/plugins/manager.ts +0 -376
- package/src/plugins/types.ts +0 -284
- package/src/scanners/cicd-scanner.ts +0 -258
- package/src/scanners/cloud-scanner.ts +0 -466
- package/src/scanners/framework-scanner.ts +0 -469
- package/src/scanners/iac-scanner.ts +0 -388
- package/src/scanners/index.ts +0 -539
- package/src/scanners/language-scanner.ts +0 -276
- package/src/scanners/package-manager-scanner.ts +0 -277
- package/src/scanners/types.ts +0 -172
- package/src/sessions/manager.ts +0 -472
- package/src/sessions/types.ts +0 -44
- package/src/sharing/sync.ts +0 -300
- package/src/sharing/viewer.ts +0 -163
- package/src/snapshots/index.ts +0 -2
- package/src/snapshots/manager.ts +0 -530
- package/src/state/artifacts.ts +0 -147
- package/src/state/audit.ts +0 -137
- package/src/state/billing.ts +0 -240
- package/src/state/checkpoints.ts +0 -117
- package/src/state/config.ts +0 -67
- package/src/state/conversations.ts +0 -14
- package/src/state/credentials.ts +0 -154
- package/src/state/db.ts +0 -58
- package/src/state/index.ts +0 -26
- package/src/state/messages.ts +0 -115
- package/src/state/projects.ts +0 -123
- package/src/state/schema.ts +0 -236
- package/src/state/sessions.ts +0 -147
- package/src/state/teams.ts +0 -200
- package/src/telemetry.ts +0 -108
- package/src/tools/aws-ops.ts +0 -952
- package/src/tools/azure-ops.ts +0 -579
- package/src/tools/file-ops.ts +0 -615
- package/src/tools/gcp-ops.ts +0 -625
- package/src/tools/git-ops.ts +0 -773
- package/src/tools/github-ops.ts +0 -799
- package/src/tools/helm-ops.ts +0 -943
- package/src/tools/index.ts +0 -17
- package/src/tools/k8s-ops.ts +0 -819
- package/src/tools/schemas/converter.ts +0 -184
- package/src/tools/schemas/devops.ts +0 -3502
- package/src/tools/schemas/index.ts +0 -73
- package/src/tools/schemas/standard.ts +0 -1148
- package/src/tools/schemas/types.ts +0 -735
- package/src/tools/spawn-exec.ts +0 -148
- package/src/tools/terraform-ops.ts +0 -862
- package/src/types/ambient.d.ts +0 -193
- package/src/types/config.ts +0 -83
- package/src/types/drift.ts +0 -116
- package/src/types/enterprise.ts +0 -335
- package/src/types/index.ts +0 -20
- package/src/types/plan.ts +0 -44
- package/src/types/request.ts +0 -65
- package/src/types/response.ts +0 -54
- package/src/types/service.ts +0 -51
- package/src/ui/App.tsx +0 -2114
- package/src/ui/DeployPreview.tsx +0 -174
- package/src/ui/FileDiffModal.tsx +0 -162
- package/src/ui/Header.tsx +0 -131
- package/src/ui/HelpModal.tsx +0 -57
- package/src/ui/InputBox.tsx +0 -503
- package/src/ui/MessageList.tsx +0 -1032
- package/src/ui/PermissionPrompt.tsx +0 -163
- package/src/ui/StatusBar.tsx +0 -277
- package/src/ui/TerminalPane.tsx +0 -84
- package/src/ui/ToolCallDisplay.tsx +0 -643
- package/src/ui/TreePane.tsx +0 -132
- package/src/ui/chat-ui.ts +0 -850
- package/src/ui/index.ts +0 -33
- package/src/ui/ink/index.ts +0 -1444
- package/src/ui/streaming.ts +0 -176
- package/src/ui/theme.ts +0 -104
- package/src/ui/types.ts +0 -75
- package/src/utils/analytics.ts +0 -72
- package/src/utils/cost-warning.ts +0 -27
- package/src/utils/env.ts +0 -46
- package/src/utils/errors.ts +0 -69
- package/src/utils/event-bus.ts +0 -38
- package/src/utils/index.ts +0 -24
- package/src/utils/logger.ts +0 -171
- package/src/utils/rate-limiter.ts +0 -121
- package/src/utils/service-auth.ts +0 -49
- package/src/utils/validation.ts +0 -53
- package/src/version.ts +0 -4
- package/src/watcher/index.ts +0 -214
- package/src/wizard/approval.ts +0 -383
- package/src/wizard/index.ts +0 -25
- package/src/wizard/prompts.ts +0 -338
- package/src/wizard/types.ts +0 -172
- package/src/wizard/ui.ts +0 -556
- package/src/wizard/wizard.ts +0 -304
- package/tsconfig.json +0 -24
|
@@ -1,176 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Subagent Tests
|
|
3
|
-
*
|
|
4
|
-
* Validates subagent creation, configuration, tool restrictions, and
|
|
5
|
-
* the @agent mention parser.
|
|
6
|
-
*/
|
|
7
|
-
|
|
8
|
-
import { describe, test, expect } from 'vitest';
|
|
9
|
-
import {
|
|
10
|
-
createSubagent,
|
|
11
|
-
parseAgentMention,
|
|
12
|
-
type SubagentType,
|
|
13
|
-
exploreConfig,
|
|
14
|
-
infraConfig,
|
|
15
|
-
securityConfig,
|
|
16
|
-
costConfig,
|
|
17
|
-
generalConfig,
|
|
18
|
-
Subagent,
|
|
19
|
-
} from '../agent/subagents/index';
|
|
20
|
-
|
|
21
|
-
// ===========================================================================
|
|
22
|
-
// createSubagent
|
|
23
|
-
// ===========================================================================
|
|
24
|
-
|
|
25
|
-
describe('createSubagent', () => {
|
|
26
|
-
test('createSubagent("explore") returns Subagent with correct config', () => {
|
|
27
|
-
const agent = createSubagent('explore');
|
|
28
|
-
expect(agent).toBeInstanceOf(Subagent);
|
|
29
|
-
expect(agent.config.name).toBe('explore');
|
|
30
|
-
expect(agent.config.model).toBe('anthropic/claude-haiku-4-5');
|
|
31
|
-
expect(agent.config.maxTurns).toBe(15);
|
|
32
|
-
});
|
|
33
|
-
|
|
34
|
-
test('createSubagent("infra") returns Subagent with correct tools', () => {
|
|
35
|
-
const agent = createSubagent('infra');
|
|
36
|
-
expect(agent.config.name).toBe('infra');
|
|
37
|
-
const toolNames = agent.config.tools.map(t => t.name);
|
|
38
|
-
expect(toolNames).toContain('read_file');
|
|
39
|
-
expect(toolNames).toContain('cloud_discover');
|
|
40
|
-
expect(toolNames).toContain('cost_estimate');
|
|
41
|
-
expect(toolNames).toContain('drift_detect');
|
|
42
|
-
});
|
|
43
|
-
|
|
44
|
-
test('createSubagent("security") returns Subagent with security prompt', () => {
|
|
45
|
-
const agent = createSubagent('security');
|
|
46
|
-
expect(agent.config.name).toBe('security');
|
|
47
|
-
expect(agent.config.systemPrompt).toContain('security');
|
|
48
|
-
expect(agent.config.systemPrompt).toContain('CRITICAL');
|
|
49
|
-
});
|
|
50
|
-
|
|
51
|
-
test('createSubagent("cost") uses haiku model', () => {
|
|
52
|
-
const agent = createSubagent('cost');
|
|
53
|
-
expect(agent.config.model).toContain('haiku');
|
|
54
|
-
});
|
|
55
|
-
|
|
56
|
-
test('createSubagent("general") has bash and webfetch tools', () => {
|
|
57
|
-
const agent = createSubagent('general');
|
|
58
|
-
const toolNames = agent.config.tools.map(t => t.name);
|
|
59
|
-
expect(toolNames).toContain('bash');
|
|
60
|
-
expect(toolNames).toContain('webfetch');
|
|
61
|
-
});
|
|
62
|
-
|
|
63
|
-
test('all subagent types are valid and produce Subagent instances', () => {
|
|
64
|
-
const types: SubagentType[] = ['explore', 'infra', 'security', 'cost', 'general'];
|
|
65
|
-
for (const type of types) {
|
|
66
|
-
const agent = createSubagent(type);
|
|
67
|
-
expect(agent).toBeInstanceOf(Subagent);
|
|
68
|
-
expect(agent.config.name).toBe(type);
|
|
69
|
-
}
|
|
70
|
-
});
|
|
71
|
-
});
|
|
72
|
-
|
|
73
|
-
// ===========================================================================
|
|
74
|
-
// parseAgentMention
|
|
75
|
-
// ===========================================================================
|
|
76
|
-
|
|
77
|
-
describe('parseAgentMention', () => {
|
|
78
|
-
test('parses "@explore find TODOs" correctly', () => {
|
|
79
|
-
const result = parseAgentMention('@explore find TODOs');
|
|
80
|
-
expect(result).not.toBeNull();
|
|
81
|
-
expect(result!.agent).toBe('explore');
|
|
82
|
-
expect(result!.prompt).toBe('find TODOs');
|
|
83
|
-
});
|
|
84
|
-
|
|
85
|
-
test('parses "@infra check EKS" correctly', () => {
|
|
86
|
-
const result = parseAgentMention('@infra check EKS');
|
|
87
|
-
expect(result).not.toBeNull();
|
|
88
|
-
expect(result!.agent).toBe('infra');
|
|
89
|
-
expect(result!.prompt).toBe('check EKS');
|
|
90
|
-
});
|
|
91
|
-
|
|
92
|
-
test('parses "@security scan for secrets" correctly', () => {
|
|
93
|
-
const result = parseAgentMention('@security scan for secrets');
|
|
94
|
-
expect(result).not.toBeNull();
|
|
95
|
-
expect(result!.agent).toBe('security');
|
|
96
|
-
expect(result!.prompt).toBe('scan for secrets');
|
|
97
|
-
});
|
|
98
|
-
|
|
99
|
-
test('parses "@cost estimate monthly spend" correctly', () => {
|
|
100
|
-
const result = parseAgentMention('@cost estimate monthly spend');
|
|
101
|
-
expect(result).not.toBeNull();
|
|
102
|
-
expect(result!.agent).toBe('cost');
|
|
103
|
-
});
|
|
104
|
-
|
|
105
|
-
test('parses "@general research topic" correctly', () => {
|
|
106
|
-
const result = parseAgentMention('@general research topic');
|
|
107
|
-
expect(result).not.toBeNull();
|
|
108
|
-
expect(result!.agent).toBe('general');
|
|
109
|
-
});
|
|
110
|
-
|
|
111
|
-
test('returns null for normal messages', () => {
|
|
112
|
-
expect(parseAgentMention('normal message without @mention')).toBeNull();
|
|
113
|
-
expect(parseAgentMention('fix the bug')).toBeNull();
|
|
114
|
-
});
|
|
115
|
-
|
|
116
|
-
test('returns null for empty string', () => {
|
|
117
|
-
expect(parseAgentMention('')).toBeNull();
|
|
118
|
-
});
|
|
119
|
-
|
|
120
|
-
test('returns null for unknown @agent prefix', () => {
|
|
121
|
-
expect(parseAgentMention('@unknown do something')).toBeNull();
|
|
122
|
-
expect(parseAgentMention('@deploy run it')).toBeNull();
|
|
123
|
-
});
|
|
124
|
-
|
|
125
|
-
test('returns null when @agent has no prompt', () => {
|
|
126
|
-
// The regex requires at least one character after the agent name
|
|
127
|
-
expect(parseAgentMention('@explore')).toBeNull();
|
|
128
|
-
});
|
|
129
|
-
});
|
|
130
|
-
|
|
131
|
-
// ===========================================================================
|
|
132
|
-
// Subagent Tool Restrictions
|
|
133
|
-
// ===========================================================================
|
|
134
|
-
|
|
135
|
-
describe('Subagent tool restrictions', () => {
|
|
136
|
-
test('all subagent configs exclude the "task" tool (no nesting)', () => {
|
|
137
|
-
const configs = [exploreConfig, infraConfig, securityConfig, costConfig, generalConfig];
|
|
138
|
-
for (const config of configs) {
|
|
139
|
-
const hasTask = config.tools.some(t => t.name === 'task');
|
|
140
|
-
expect(hasTask).toBe(false);
|
|
141
|
-
}
|
|
142
|
-
});
|
|
143
|
-
|
|
144
|
-
test('explore subagent only has read-only tools', () => {
|
|
145
|
-
const toolNames = exploreConfig.tools.map(t => t.name);
|
|
146
|
-
expect(toolNames).toEqual(['read_file', 'glob', 'grep', 'list_dir']);
|
|
147
|
-
// None of these are destructive
|
|
148
|
-
for (const tool of exploreConfig.tools) {
|
|
149
|
-
expect(tool.isDestructive).toBeFalsy();
|
|
150
|
-
}
|
|
151
|
-
});
|
|
152
|
-
|
|
153
|
-
test('security subagent only has read-only tools', () => {
|
|
154
|
-
const toolNames = securityConfig.tools.map(t => t.name);
|
|
155
|
-
expect(toolNames).toEqual(['read_file', 'glob', 'grep', 'list_dir']);
|
|
156
|
-
for (const tool of securityConfig.tools) {
|
|
157
|
-
expect(tool.isDestructive).toBeFalsy();
|
|
158
|
-
}
|
|
159
|
-
});
|
|
160
|
-
|
|
161
|
-
test('infra subagent has cloud discovery tools', () => {
|
|
162
|
-
const toolNames = infraConfig.tools.map(t => t.name);
|
|
163
|
-
expect(toolNames).toContain('cloud_discover');
|
|
164
|
-
expect(toolNames).toContain('cost_estimate');
|
|
165
|
-
expect(toolNames).toContain('drift_detect');
|
|
166
|
-
});
|
|
167
|
-
|
|
168
|
-
test('cost subagent has cost_estimate and cloud_discover', () => {
|
|
169
|
-
const toolNames = costConfig.tools.map(t => t.name);
|
|
170
|
-
expect(toolNames).toContain('cost_estimate');
|
|
171
|
-
expect(toolNames).toContain('cloud_discover');
|
|
172
|
-
// But should not have destructive tools
|
|
173
|
-
expect(toolNames).not.toContain('terraform');
|
|
174
|
-
expect(toolNames).not.toContain('kubectl');
|
|
175
|
-
});
|
|
176
|
-
});
|
|
@@ -1,248 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* System Prompt Tests
|
|
3
|
-
*
|
|
4
|
-
* Validates that buildSystemPrompt assembles the correct prompt sections
|
|
5
|
-
* based on mode, tools, NIMBUS.md, subagent state, and environment context.
|
|
6
|
-
*/
|
|
7
|
-
|
|
8
|
-
import { describe, test, expect, beforeEach, afterEach } from 'vitest';
|
|
9
|
-
import * as fs from 'node:fs';
|
|
10
|
-
import * as path from 'node:path';
|
|
11
|
-
import * as os from 'node:os';
|
|
12
|
-
import { buildSystemPrompt, loadNimbusMd, extractForbiddenRules } from '../agent/system-prompt';
|
|
13
|
-
import type { ToolDefinition } from '../tools/schemas/types';
|
|
14
|
-
import { z } from 'zod';
|
|
15
|
-
|
|
16
|
-
// ---------------------------------------------------------------------------
|
|
17
|
-
// Helpers
|
|
18
|
-
// ---------------------------------------------------------------------------
|
|
19
|
-
|
|
20
|
-
/** Create a minimal ToolDefinition for prompt tests. */
|
|
21
|
-
function makeTool(name: string): ToolDefinition {
|
|
22
|
-
return {
|
|
23
|
-
name,
|
|
24
|
-
description: `Description of ${name}`,
|
|
25
|
-
inputSchema: z.object({}),
|
|
26
|
-
execute: async () => ({ output: 'ok', isError: false }),
|
|
27
|
-
permissionTier: 'auto_allow',
|
|
28
|
-
category: 'standard',
|
|
29
|
-
};
|
|
30
|
-
}
|
|
31
|
-
|
|
32
|
-
// ---------------------------------------------------------------------------
|
|
33
|
-
// Temp directory for NIMBUS.md tests
|
|
34
|
-
// ---------------------------------------------------------------------------
|
|
35
|
-
|
|
36
|
-
let tmpDir: string;
|
|
37
|
-
|
|
38
|
-
beforeEach(() => {
|
|
39
|
-
tmpDir = fs.mkdtempSync(path.join(os.tmpdir(), 'nimbus-prompt-test-'));
|
|
40
|
-
});
|
|
41
|
-
|
|
42
|
-
afterEach(() => {
|
|
43
|
-
fs.rmSync(tmpDir, { recursive: true, force: true });
|
|
44
|
-
});
|
|
45
|
-
|
|
46
|
-
// ===========================================================================
|
|
47
|
-
// buildSystemPrompt
|
|
48
|
-
// ===========================================================================
|
|
49
|
-
|
|
50
|
-
describe('buildSystemPrompt', () => {
|
|
51
|
-
test('includes base identity', () => {
|
|
52
|
-
const prompt = buildSystemPrompt({ mode: 'build', tools: [] });
|
|
53
|
-
expect(prompt).toContain('You are Nimbus');
|
|
54
|
-
// C2: new DevOps-operator-first framing
|
|
55
|
-
expect(prompt).toContain('autonomous DevOps operator');
|
|
56
|
-
expect(prompt).toContain('RUN commands and query live state');
|
|
57
|
-
});
|
|
58
|
-
|
|
59
|
-
test('includes mode-specific instructions for "plan"', () => {
|
|
60
|
-
const prompt = buildSystemPrompt({ mode: 'plan', tools: [] });
|
|
61
|
-
expect(prompt).toContain('Mode: PLAN');
|
|
62
|
-
expect(prompt).toContain('NOT allowed');
|
|
63
|
-
});
|
|
64
|
-
|
|
65
|
-
test('includes mode-specific instructions for "build"', () => {
|
|
66
|
-
const prompt = buildSystemPrompt({ mode: 'build', tools: [] });
|
|
67
|
-
expect(prompt).toContain('Mode: BUILD');
|
|
68
|
-
expect(prompt).toContain('Edit and create files');
|
|
69
|
-
});
|
|
70
|
-
|
|
71
|
-
test('includes mode-specific instructions for "deploy"', () => {
|
|
72
|
-
const prompt = buildSystemPrompt({ mode: 'deploy', tools: [] });
|
|
73
|
-
expect(prompt).toContain('Mode: DEPLOY');
|
|
74
|
-
expect(prompt).toContain('terraform apply');
|
|
75
|
-
});
|
|
76
|
-
|
|
77
|
-
test('includes tool-use guidelines', () => {
|
|
78
|
-
const prompt = buildSystemPrompt({ mode: 'build', tools: [] });
|
|
79
|
-
expect(prompt).toContain('Tool-Use Guidelines');
|
|
80
|
-
expect(prompt).toContain('read_file');
|
|
81
|
-
});
|
|
82
|
-
|
|
83
|
-
test('includes tools summary with correct count', () => {
|
|
84
|
-
const tools = [makeTool('alpha'), makeTool('beta'), makeTool('gamma')];
|
|
85
|
-
const prompt = buildSystemPrompt({ mode: 'build', tools });
|
|
86
|
-
expect(prompt).toContain('Available Tools (3)');
|
|
87
|
-
expect(prompt).toContain('**alpha**');
|
|
88
|
-
expect(prompt).toContain('**beta**');
|
|
89
|
-
expect(prompt).toContain('**gamma**');
|
|
90
|
-
});
|
|
91
|
-
|
|
92
|
-
test('includes NIMBUS.md content when provided', () => {
|
|
93
|
-
const prompt = buildSystemPrompt({
|
|
94
|
-
mode: 'build',
|
|
95
|
-
tools: [],
|
|
96
|
-
nimbusInstructions: 'Always use TypeScript strict mode.',
|
|
97
|
-
});
|
|
98
|
-
expect(prompt).toContain('Project Instructions (NIMBUS.md)');
|
|
99
|
-
expect(prompt).toContain('Always use TypeScript strict mode.');
|
|
100
|
-
});
|
|
101
|
-
|
|
102
|
-
test('includes environment context', () => {
|
|
103
|
-
const prompt = buildSystemPrompt({
|
|
104
|
-
mode: 'build',
|
|
105
|
-
tools: [],
|
|
106
|
-
cwd: tmpDir,
|
|
107
|
-
});
|
|
108
|
-
expect(prompt).toContain('# Environment');
|
|
109
|
-
expect(prompt).toContain(`Working directory: ${tmpDir}`);
|
|
110
|
-
expect(prompt).toContain(`Platform: ${process.platform}`);
|
|
111
|
-
});
|
|
112
|
-
|
|
113
|
-
test('includes subagent instructions when activeSubagent set', () => {
|
|
114
|
-
const prompt = buildSystemPrompt({
|
|
115
|
-
mode: 'build',
|
|
116
|
-
tools: [],
|
|
117
|
-
activeSubagent: 'explore',
|
|
118
|
-
});
|
|
119
|
-
expect(prompt).toContain('Subagent Mode: explore');
|
|
120
|
-
expect(prompt).toContain('Do NOT spawn further subagents');
|
|
121
|
-
});
|
|
122
|
-
|
|
123
|
-
test('does not include subagent section when activeSubagent is not set', () => {
|
|
124
|
-
const prompt = buildSystemPrompt({ mode: 'build', tools: [] });
|
|
125
|
-
expect(prompt).not.toContain('Subagent Mode');
|
|
126
|
-
});
|
|
127
|
-
|
|
128
|
-
test('includes date in environment context', () => {
|
|
129
|
-
const prompt = buildSystemPrompt({ mode: 'build', tools: [] });
|
|
130
|
-
// Should contain a date-like string YYYY-MM-DD
|
|
131
|
-
expect(prompt).toMatch(/Date: \d{4}-\d{2}-\d{2}/);
|
|
132
|
-
});
|
|
133
|
-
});
|
|
134
|
-
|
|
135
|
-
// ===========================================================================
|
|
136
|
-
// loadNimbusMd
|
|
137
|
-
// ===========================================================================
|
|
138
|
-
|
|
139
|
-
describe('loadNimbusMd', () => {
|
|
140
|
-
test('returns null when no file exists', () => {
|
|
141
|
-
const result = loadNimbusMd(tmpDir);
|
|
142
|
-
expect(result).toBeNull();
|
|
143
|
-
});
|
|
144
|
-
|
|
145
|
-
test('loads NIMBUS.md from cwd', () => {
|
|
146
|
-
const content = '# Custom Instructions\nDo the thing.';
|
|
147
|
-
fs.writeFileSync(path.join(tmpDir, 'NIMBUS.md'), content, 'utf-8');
|
|
148
|
-
const result = loadNimbusMd(tmpDir);
|
|
149
|
-
expect(result).toBe(content);
|
|
150
|
-
});
|
|
151
|
-
|
|
152
|
-
test('loads NIMBUS.md from .nimbus subdirectory', () => {
|
|
153
|
-
const nimbusDir = path.join(tmpDir, '.nimbus');
|
|
154
|
-
fs.mkdirSync(nimbusDir, { recursive: true });
|
|
155
|
-
const content = 'Sub-dir instructions';
|
|
156
|
-
fs.writeFileSync(path.join(nimbusDir, 'NIMBUS.md'), content, 'utf-8');
|
|
157
|
-
const result = loadNimbusMd(tmpDir);
|
|
158
|
-
expect(result).toBe(content);
|
|
159
|
-
});
|
|
160
|
-
|
|
161
|
-
test('prefers cwd NIMBUS.md over .nimbus subdirectory', () => {
|
|
162
|
-
// Write both
|
|
163
|
-
fs.writeFileSync(path.join(tmpDir, 'NIMBUS.md'), 'root-level', 'utf-8');
|
|
164
|
-
const nimbusDir = path.join(tmpDir, '.nimbus');
|
|
165
|
-
fs.mkdirSync(nimbusDir, { recursive: true });
|
|
166
|
-
fs.writeFileSync(path.join(nimbusDir, 'NIMBUS.md'), 'sub-level', 'utf-8');
|
|
167
|
-
|
|
168
|
-
const result = loadNimbusMd(tmpDir);
|
|
169
|
-
expect(result).toBe('root-level');
|
|
170
|
-
});
|
|
171
|
-
});
|
|
172
|
-
|
|
173
|
-
// ===========================================================================
|
|
174
|
-
// G14: extractForbiddenRules
|
|
175
|
-
// ===========================================================================
|
|
176
|
-
|
|
177
|
-
describe('extractForbiddenRules (G14)', () => {
|
|
178
|
-
test('extracts bullet items from ## Forbidden section', () => {
|
|
179
|
-
const content = `
|
|
180
|
-
## Safety Rules
|
|
181
|
-
|
|
182
|
-
- Do not break prod
|
|
183
|
-
|
|
184
|
-
## Forbidden
|
|
185
|
-
|
|
186
|
-
- Never destroy the production database
|
|
187
|
-
- Never delete the S3 bucket
|
|
188
|
-
- Never run rm -rf /
|
|
189
|
-
|
|
190
|
-
## Custom Instructions
|
|
191
|
-
|
|
192
|
-
Some other stuff
|
|
193
|
-
`;
|
|
194
|
-
const rules = extractForbiddenRules(content);
|
|
195
|
-
expect(rules).toHaveLength(3);
|
|
196
|
-
expect(rules[0]).toBe('Never destroy the production database');
|
|
197
|
-
expect(rules[1]).toBe('Never delete the S3 bucket');
|
|
198
|
-
expect(rules[2]).toBe('Never run rm -rf /');
|
|
199
|
-
});
|
|
200
|
-
|
|
201
|
-
test('returns empty array when no Forbidden section', () => {
|
|
202
|
-
const content = '## Safety Rules\n\n- Be careful\n';
|
|
203
|
-
expect(extractForbiddenRules(content)).toEqual([]);
|
|
204
|
-
});
|
|
205
|
-
|
|
206
|
-
test('ignores HTML comment lines', () => {
|
|
207
|
-
const content = `
|
|
208
|
-
## Forbidden
|
|
209
|
-
|
|
210
|
-
<!-- Example: - Never destroy the database -->
|
|
211
|
-
- Never touch prod
|
|
212
|
-
`;
|
|
213
|
-
const rules = extractForbiddenRules(content);
|
|
214
|
-
expect(rules).toHaveLength(1);
|
|
215
|
-
expect(rules[0]).toBe('Never touch prod');
|
|
216
|
-
});
|
|
217
|
-
|
|
218
|
-
test('G14: prompt includes HARD CONSTRAINTS block when Forbidden section has entries', () => {
|
|
219
|
-
const nimbusContent = `
|
|
220
|
-
## Forbidden
|
|
221
|
-
|
|
222
|
-
- Never destroy the production database
|
|
223
|
-
- Never run terraform destroy in prod
|
|
224
|
-
`;
|
|
225
|
-
const prompt = buildSystemPrompt({
|
|
226
|
-
mode: 'build',
|
|
227
|
-
tools: [],
|
|
228
|
-
nimbusInstructions: nimbusContent,
|
|
229
|
-
});
|
|
230
|
-
expect(prompt).toContain('HARD CONSTRAINTS');
|
|
231
|
-
expect(prompt).toContain('Never destroy the production database');
|
|
232
|
-
expect(prompt).toContain('STRICTLY FORBIDDEN');
|
|
233
|
-
});
|
|
234
|
-
|
|
235
|
-
test('G14: prompt does not include HARD CONSTRAINTS when Forbidden section is empty/comments', () => {
|
|
236
|
-
const nimbusContent = `
|
|
237
|
-
## Forbidden
|
|
238
|
-
|
|
239
|
-
<!-- List operations Nimbus must never perform in this project -->
|
|
240
|
-
`;
|
|
241
|
-
const prompt = buildSystemPrompt({
|
|
242
|
-
mode: 'build',
|
|
243
|
-
tools: [],
|
|
244
|
-
nimbusInstructions: nimbusContent,
|
|
245
|
-
});
|
|
246
|
-
expect(prompt).not.toContain('HARD CONSTRAINTS');
|
|
247
|
-
});
|
|
248
|
-
});
|