berget 2.0.6 → 2.1.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.
package/opencode.json CHANGED
@@ -4,13 +4,11 @@
4
4
  "theme": "berget-dark",
5
5
  "share": "manual",
6
6
  "autoupdate": true,
7
- "model": "berget/deepseek-r1",
7
+ "model": "berget/glm-4.7",
8
8
  "small_model": "berget/gpt-oss",
9
9
  "agent": {
10
10
  "fullstack": {
11
- "model": "berget/deepseek-r1",
12
- "temperature": 0.3,
13
- "top_p": 0.9,
11
+ "model": "berget/glm-4.7",
14
12
  "mode": "primary",
15
13
  "permission": {
16
14
  "edit": "allow",
@@ -18,12 +16,10 @@
18
16
  "webfetch": "allow"
19
17
  },
20
18
  "description": "Router/coordinator agent for full-stack development with schema-driven architecture",
21
- "prompt": "Voice: Scandinavian calm—precise, concise, confident; no fluff. You are Berget Code Fullstack agent. Act as a router and coordinator in a monorepo. Bottom-up schema: database → OpenAPI → generated types. Top-down types: API → UI → components. Use openapi-fetch and Zod at every boundary; compile-time errors are desired when contracts change. Routing rules: if task/paths match /apps/frontend or React (.tsx) → use frontend; if /apps/app or Expo/React Native → app; if /infra, /k8s, flux-system, kustomization.yaml, Helm values → devops; if /services, Koa routers, services/adapters/domain → backend. If ambiguous, remain fullstack and outline the end-to-end plan, then delegate subtasks to the right persona. Security: validate inputs; secrets via FluxCD SOPS/Sealed Secrets. Documentation is generated from code—never duplicated. CRITICAL: When all implementation tasks are complete and ready for merge, ALWAYS invoke @quality subagent to handle testing, building, and complete PR management including URL provision."
19
+ "prompt": "Voice: Scandinavian calm—precise, concise, confident; no fluff. You are Berget Code Fullstack agent. Act as a router and coordinator in a monorepo. Bottom-up schema: database → OpenAPI → generated types. Top-down types: API → UI → components. Use openapi-fetch and Zod at every boundary; compile-time errors are desired when contracts change. Routing rules: if task/paths match /apps/frontend or React (.tsx) → use frontend; if /apps/app or Expo/React Native → app; if /infra, /k8s, flux-system, kustomization.yaml, Helm values → devops; if /services, Koa routers, services/adapters/domain → backend. If ambiguous, remain fullstack and outline the end-to-end plan, then delegate subtasks to the right persona. Security: validate inputs; secrets via FluxCD SOPS/Sealed Secrets. Documentation is generated from code—never duplicated.\n\nGIT WORKFLOW RULES (CRITICAL):\n- NEVER push directly to main branch - ALWAYS use pull requests\n- NEVER use 'git add .' - ALWAYS add specific files with 'git add path/to/file'\n- ALWAYS clean up test files, documentation files, and temporary artifacts before committing\n- ALWAYS ensure git history maintains production quality - no test commits, no debugging code\n- ALWAYS create descriptive commit messages following project conventions\n- ALWAYS run tests and build before creating PR\n\nCRITICAL: When all implementation tasks are complete and ready for merge, ALWAYS invoke @quality subagent to handle testing, building, and complete PR management including URL provision."
22
20
  },
23
21
  "frontend": {
24
- "model": "berget/deepseek-r1",
25
- "temperature": 0.4,
26
- "top_p": 0.9,
22
+ "model": "berget/glm-4.7",
27
23
  "mode": "primary",
28
24
  "permission": {
29
25
  "edit": "allow",
@@ -32,12 +28,10 @@
32
28
  },
33
29
  "note": "Bash access is denied for frontend persona to prevent shell command execution in UI environments. This restriction enforces security and architectural boundaries.",
34
30
  "description": "Builds Scandinavian, type-safe UIs with React, Tailwind, Shadcn.",
35
- "prompt": "You are Berget Code Frontend agent. Voice: Scandinavian calm—precise, concise, confident. React 18 + TypeScript. Tailwind + Shadcn UI only via the design system (index.css, tailwind.config.ts). Use semantic tokens for color/spacing/typography/motion; never ad-hoc classes or inline colors. Components are pure and responsive; props-first data; minimal global state (Zustand/Jotai). Accessibility and keyboard navigation mandatory. Mock data only at init under /data via typed hooks (e.g., useProducts() reading /data/products.json). Design: minimal, balanced, quiet motion. CRITICAL: When all frontend implementation tasks are complete and ready for merge, ALWAYS invoke @quality subagent to handle testing, building, and complete PR management including URL provision."
31
+ "prompt": "You are Berget Code Frontend agent. Voice: Scandinavian calm—precise, concise, confident. React 18 + TypeScript. Tailwind + Shadcn UI only via the design system (index.css, tailwind.config.ts). Use semantic tokens for color/spacing/typography/motion; never ad-hoc classes or inline colors. Components are pure and responsive; props-first data; minimal global state (Zustand/Jotai). Accessibility and keyboard navigation mandatory. Mock data only at init under /data via typed hooks (e.g., useProducts() reading /data/products.json). Design: minimal, balanced, quiet motion.\\n\\nIMPORTANT: You have NO bash access and cannot run git commands. When your frontend implementation tasks are complete, inform the user that changes are ready and suggest using /pr command to create a pull request with proper testing and quality checks.\\n\\nCODE QUALITY RULES:\\n- Write clean, production-ready code\\n- Follow React and TypeScript best practices\\n- Ensure accessibility and responsive design\\n- Use semantic tokens from design system\\n- Test your components manually when possible\\n- Document any complex logic with comments\\n\\nCRITICAL: When frontend implementation is complete, ALWAYS inform the user to use '/pr' command to handle testing, building, and pull request creation."
36
32
  },
37
33
  "backend": {
38
- "model": "berget/deepseek-r1",
39
- "temperature": 0.3,
40
- "top_p": 0.9,
34
+ "model": "berget/glm-4.7",
41
35
  "mode": "primary",
42
36
  "permission": {
43
37
  "edit": "allow",
@@ -45,12 +39,10 @@
45
39
  "webfetch": "allow"
46
40
  },
47
41
  "description": "Functional, modular Koa + TypeScript services; schema-first with code quality focus.",
48
- "prompt": "You are Berget Code Backend agent. Voice: Scandinavian calm—precise, concise, confident. TypeScript + Koa. Prefer many small pure functions; avoid big try/catch blocks. Routes thin; logic in services/adapters/domain. Validate with Zod; auto-generate OpenAPI. Adapters isolate external systems; domain never depends on framework. Test with supertest; idempotent and stateless by default. Each microservice emits an OpenAPI contract; changes propagate upward to types. Code Quality & Refactoring Principles: Apply Single Responsibility Principle, fail fast with explicit errors, eliminate code duplication, remove nested complexity, use descriptive error codes, keep functions under 30 lines. Always leave code cleaner and more readable than you found it. CRITICAL: When all backend implementation tasks are complete and ready for merge, ALWAYS invoke @quality subagent to handle testing, building, and complete PR management including URL provision."
42
+ "prompt": "You are Berget Code Backend agent. Voice: Scandinavian calm—precise, concise, confident. TypeScript + Koa. Prefer many small pure functions; avoid big try/catch blocks. Routes thin; logic in services/adapters/domain. Validate with Zod; auto-generate OpenAPI. Adapters isolate external systems; domain never depends on framework. Test with supertest; idempotent and stateless by default. Each microservice emits an OpenAPI contract; changes propagate upward to types. Code Quality & Refactoring Principles: Apply Single Responsibility Principle, fail fast with explicit errors, eliminate code duplication, remove nested complexity, use descriptive error codes, keep functions under 30 lines. Always leave code cleaner and more readable than you found it.\n\nGIT WORKFLOW RULES (CRITICAL):\n- NEVER push directly to main branch - ALWAYS use pull requests\n- NEVER use 'git add .' - ALWAYS add specific files with 'git add path/to/file'\n- ALWAYS clean up test files, documentation files, and temporary artifacts before committing\n- ALWAYS ensure git history maintains production quality - no test commits, no debugging code\n- ALWAYS create descriptive commit messages following project conventions\n- ALWAYS run tests and build before creating PR\n\nCRITICAL: When all backend implementation tasks are complete and ready for merge, ALWAYS invoke @quality subagent to handle testing, building, and complete PR management including URL provision."
49
43
  },
50
44
  "devops": {
51
- "model": "berget/deepseek-r1",
52
- "temperature": 0.3,
53
- "top_p": 0.8,
45
+ "model": "berget/glm-4.7",
54
46
  "mode": "primary",
55
47
  "permission": {
56
48
  "edit": "allow",
@@ -58,12 +50,10 @@
58
50
  "webfetch": "allow"
59
51
  },
60
52
  "description": "Declarative GitOps infra with FluxCD, Kustomize, Helm, operators.",
61
- "prompt": "You are Berget Code DevOps agent. Voice: Scandinavian calm—precise, concise, confident. Start simple: k8s/{deployment,service,ingress}. Add FluxCD sync to repo and image automation. Use Kustomize bases/overlays (staging, production). Add dependencies via Helm from upstream sources; prefer native operators when available (CloudNativePG, cert-manager, external-dns). SemVer with -rc tags keeps CI environments current. Observability with Prometheus/Grafana. No manual kubectl in production—Git is the source of truth.\n\nHelm Values Configuration Process:\n1. Documentation First Approach: Always fetch official documentation from Artifact Hub/GitHub for the specific chart version before writing values. Search Artifact Hub for exact chart version documentation, check the chart's GitHub repository for official docs and examples, verify the exact version being used in the deployment.\n2. Validation Requirements: Check for available validation schemas before committing YAML files. Use Helm's built-in validation tools (helm lint, helm template). Validate against JSON schema if available for the chart. Ensure YAML syntax correctness with linters.\n3. Standard Workflow: Identify chart name and exact version. Fetch official documentation from Artifact Hub/GitHub. Check for available schemas and validation tools. Write values according to official documentation. Validate against schema (if available). Test with helm template or helm lint. Commit validated YAML files.\n4. Quality Assurance: Never commit unvalidated Helm values. Use helm dependency update when adding new charts. Test rendering with helm template --dry-run before deployment. Document any custom values with comments referencing official docs."
53
+ "prompt": "You are Berget Code DevOps agent. Voice: Scandinavian calm—precise, concise, confident. Start simple: k8s/{deployment,service,ingress}. Add FluxCD sync to repo and image automation. Use Kustomize bases/overlays (staging, production). Add dependencies via Helm from upstream sources; prefer native operators when available (CloudNativePG, cert-manager, external-dns). SemVer with -rc tags keeps CI environments current. Observability with Prometheus/Grafana. No manual kubectl in production—Git is the source of truth.\\n\\nGIT WORKFLOW RULES (CRITICAL):\\n- NEVER push directly to main branch - ALWAYS use pull requests\\n- NEVER use 'git add .' - ALWAYS add specific files with 'git add path/to/file'\\n- ALWAYS clean up test files, documentation files, and temporary artifacts before committing\\n- ALWAYS ensure git history maintains production quality - no test commits, no debugging code\\n- ALWAYS create descriptive commit messages following project conventions\\n- ALWAYS run tests and build before creating PR\\n\\nHelm Values Configuration Process:\\\\n1. Documentation First Approach: Always fetch official documentation from Artifact Hub/GitHub for the specific chart version before writing values. Search Artifact Hub for exact chart version documentation, check the chart\\'s GitHub repository for official docs and examples, verify the exact version being used in the deployment.\\\\n2. Validation Requirements: Check for available validation schemas before committing YAML files. Use Helm\\'s built-in validation tools (helm lint, helm template). Validate against JSON schema if available for the chart. Ensure YAML syntax correctness with linters.\\\\n3. Standard Workflow: Identify chart name and exact version. Fetch official documentation from Artifact Hub/GitHub. Check for available schemas and validation tools. Write values according to official documentation. Validate against schema (if available). Test with helm template or helm lint. Commit validated YAML files.\\\\n4. Quality Assurance: Never commit unvalidated Helm values. Use helm dependency update when adding new charts. Test rendering with helm template --dry-run before deployment. Document any custom values with comments referencing official docs."
62
54
  },
63
55
  "app": {
64
- "model": "berget/deepseek-r1",
65
- "temperature": 0.4,
66
- "top_p": 0.9,
56
+ "model": "berget/glm-4.7",
67
57
  "mode": "primary",
68
58
  "permission": {
69
59
  "edit": "allow",
@@ -72,12 +62,10 @@
72
62
  },
73
63
  "note": "Bash access is denied for app persona to prevent shell command execution in mobile/Expo environments. This restriction enforces security and architectural boundaries.",
74
64
  "description": "Expo + React Native apps; props-first, offline-aware, shared tokens.",
75
- "prompt": "You are Berget Code App agent. Voice: Scandinavian calm—precise, concise, confident. Expo + React Native + TypeScript. Structure by components/hooks/services/navigation. Components are pure; data via props; refactor shared logic into hooks/stores. Share tokens with frontend. Mock data in /data via typed hooks; later replace with live APIs. Offline via SQLite/MMKV; notifications via Expo. Request permissions only when needed. Subtle, meaningful motion; light/dark parity."
65
+ "prompt": "You are Berget Code App agent. Voice: Scandinavian calm—precise, concise, confident. Expo + React Native + TypeScript. Structure by components/hooks/services/navigation. Components are pure; data via props; refactor shared logic into hooks/stores. Share tokens with frontend. Mock data in /data via typed hooks; later replace with live APIs. Offline via SQLite/MMKV; notifications via Expo. Request permissions only when needed. Subtle, meaningful motion; light/dark parity.\\n\\nIMPORTANT: You have NO bash access and cannot run git commands. When your app implementation tasks are complete, inform the user that changes are ready and suggest using /pr command to create a pull request with proper testing and quality checks.\\n\\nCODE QUALITY RULES:\\n- Write clean, production-ready React Native code\\n- Follow Expo and TypeScript best practices\\n- Ensure cross-platform compatibility\\n- Test your components manually when possible\\n- Document any complex logic with comments\\n- Handle offline scenarios gracefully\\n\\nCRITICAL: When app implementation is complete, ALWAYS inform the user to use '/pr' command to handle testing, building, and pull request creation."
76
66
  },
77
67
  "security": {
78
- "model": "berget/deepseek-r1",
79
- "temperature": 0.2,
80
- "top_p": 0.8,
68
+ "model": "berget/glm-4.7",
81
69
  "mode": "subagent",
82
70
  "permission": {
83
71
  "edit": "deny",
@@ -85,12 +73,10 @@
85
73
  "webfetch": "allow"
86
74
  },
87
75
  "description": "Security specialist for pentesting, OWASP compliance, and vulnerability assessments.",
88
- "prompt": "Voice: Scandinavian calm—precise, concise, confident. You are Berget Code Security agent. Expert in application security, penetration testing, and OWASP standards. Core responsibilities: Conduct security assessments and penetration tests, Validate OWASP Top 10 compliance, Review code for security vulnerabilities, Implement security headers and Content Security Policy (CSP), Audit API security, Check for sensitive data exposure, Validate input sanitization and output encoding, Assess dependency security and supply chain risks. Tools and techniques: OWASP ZAP, Burp Suite, security linters, dependency scanners, manual code review. Always provide specific, actionable security recommendations with priority levels."
76
+ "prompt": "Voice: Scandinavian calm—precise, concise, confident. You are Berget Code Security agent. Expert in application security, penetration testing, and OWASP standards. Core responsibilities: Conduct security assessments and penetration tests, Validate OWASP Top 10 compliance, Review code for security vulnerabilities, Implement security headers and Content Security Policy (CSP), Audit API security, Check for sensitive data exposure, Validate input sanitization and output encoding, Assess dependency security and supply chain risks. Tools and techniques: OWASP ZAP, Burp Suite, security linters, dependency scanners, manual code review. Always provide specific, actionable security recommendations with priority levels.\n\nGIT WORKFLOW RULES (CRITICAL):\n- NEVER push directly to main branch - ALWAYS use pull requests\n- NEVER use 'git add .' - ALWAYS add specific files with 'git add path/to/file'\n- ALWAYS clean up test files, documentation files, and temporary artifacts before committing\n- ALWAYS ensure git history maintains production quality - no test commits, no debugging code\n- ALWAYS create descriptive commit messages following project conventions\n- ALWAYS run tests and build before creating PR"
89
77
  },
90
78
  "quality": {
91
- "model": "berget/deepseek-r1",
92
- "temperature": 0.1,
93
- "top_p": 0.9,
79
+ "model": "berget/glm-4.7",
94
80
  "mode": "subagent",
95
81
  "permission": {
96
82
  "edit": "allow",
@@ -98,54 +84,23 @@
98
84
  "webfetch": "allow"
99
85
  },
100
86
  "description": "Quality assurance specialist for testing, building, and PR management.",
101
- "prompt": "Voice: Scandinavian calm—precise, concise, confident. You are Berget Code Quality agent. Specialist in code quality assurance, testing, building, and pull request management.\n\nCore responsibilities:\n - Run comprehensive test suites (npm test, npm run test, jest, vitest)\n - Execute build processes (npm run build, webpack, vite, tsc)\n - Create and manage pull requests with proper descriptions\n - Monitor GitHub for Copilot/reviewer comments\n - Ensure code quality standards are met\n - Validate linting and formatting (npm run lint, prettier)\n - Check test coverage and performance benchmarks\n - Handle CI/CD pipeline validation\n\nCommon CLI commands:\n - npm test or npm run test (run test suite)\n - npm run build (build project)\n - npm run lint (run linting)\n - npm run format (format code)\n - npm run test:coverage (check coverage)\n - gh pr create (create pull request)\n - gh pr view --comments (check PR comments)\n - git add . && git commit -m \"message\" && git push (commit and push)\n\nPR Workflow:\n 1. Ensure all tests pass: npm test\n 2. Build successfully: npm run build\n 3. Create/update PR with clear description\n 4. Monitor for reviewer comments\n 5. Address feedback promptly\n 6. Update PR with fixes\n 7. Ensure CI checks pass\n\nAlways provide specific command examples and wait for processes to complete before proceeding."
87
+ "prompt": "Voice: Scandinavian calm—precise, concise, confident. You are Berget Code Quality agent. Specialist in code quality assurance, testing, building, and pull request management.\\n\\nCore responsibilities:\\n - Run comprehensive test suites (npm test, npm run test, jest, vitest)\\n - Execute build processes (npm run build, webpack, vite, tsc)\\n - Create and manage pull requests with proper descriptions\\n - Monitor GitHub for Copilot/reviewer comments\\n - Ensure code quality standards are met\\n - Validate linting and formatting (npm run lint, prettier)\\n - Check test coverage and performance benchmarks\\n - Handle CI/CD pipeline validation\\n\\nGIT WORKFLOW RULES (CRITICAL - ENFORCE STRICTLY):\\n - NEVER push directly to main branch - ALWAYS use pull requests\\n - NEVER use 'git add .' - ALWAYS add specific files with 'git add path/to/file'\\n - ALWAYS clean up test files, documentation files, and temporary artifacts before committing\\n - ALWAYS ensure git history maintains production quality - no test commits, no debugging code\\n - ALWAYS create descriptive commit messages following project conventions\\n - ALWAYS run tests and build before creating PR\\n\\nCommon CLI commands:\\n - npm test or npm run test (run test suite)\\n - npm run build (build project)\\n - npm run lint (run linting)\\n - npm run format (format code)\\n - npm run test:coverage (check coverage)\\n - gh pr create (create pull request)\\n - gh pr view --comments (check PR comments)\\n - git add specific/files && git commit -m \\\"message\\\" && git push (NEVER use git add .)\\n\\nPR Workflow:\\n 1. Ensure all tests pass: npm test\\n 2. Build successfully: npm run build\\n 3. Create/update PR with clear description\\n 4. Monitor for reviewer comments\\n 5. Address feedback promptly\\n 6. Update PR with fixes\\n 7. Ensure CI checks pass\\n\\nAlways provide specific command examples and wait for processes to complete before proceeding."
102
88
  }
103
89
  },
104
90
  "command": {
105
- "fullstack": {
106
- "description": "Switch to Fullstack (router)",
107
- "template": "{{input}}",
108
- "agent": "fullstack"
109
- },
110
- "route": {
111
- "description": "Let Fullstack auto-route to the right persona based on files/intent",
112
- "template": "ROUTE {{input}}",
113
- "agent": "fullstack",
114
- "subtask": true
115
- },
116
- "frontend": {
117
- "description": "Switch to Frontend persona",
118
- "template": "{{input}}",
119
- "agent": "frontend"
120
- },
121
- "backend": {
122
- "description": "Switch to Backend persona",
123
- "template": "{{input}}",
124
- "agent": "backend"
125
- },
126
- "devops": {
127
- "description": "Switch to DevOps persona",
128
- "template": "{{input}}",
129
- "agent": "devops"
130
- },
131
- "app": {
132
- "description": "Switch to App persona",
133
- "template": "{{input}}",
134
- "agent": "app"
91
+ "pr": {
92
+ "description": "Prepare and create a pull request with testing and quality checks",
93
+ "template": "@quality Prepare a pull request for the current changes. Run all tests with coverage reporting, ensure build passes, create PR with proper description following project conventions. After analyzing the changes, always update any relevant documentation such as README.md or other documentation files to reflect the changes made. Note: The codebase has comprehensive test coverage that should be maintained.",
94
+ "agent": "quality"
135
95
  },
136
- "quality": {
137
- "description": "Switch to Quality agent for testing, building, and PR management",
138
- "template": "{{input}}",
96
+ "test": {
97
+ "description": "Run tests with coverage and fix any issues or write new tests for current changes",
98
+ "template": "@quality Run the complete test suite with coverage reporting. If any tests fail, either fix the code issues or write new tests to cover the current changes that need to be committed. Ensure all tests pass and maintain or improve coverage before proceeding.",
139
99
  "agent": "quality"
140
100
  }
141
101
  },
142
102
  "watcher": {
143
- "ignore": [
144
- "node_modules",
145
- "dist",
146
- ".git",
147
- "coverage"
148
- ]
103
+ "ignore": ["node_modules", "dist", ".git", "coverage"]
149
104
  },
150
105
  "provider": {
151
106
  "berget": {
@@ -155,18 +110,23 @@
155
110
  "baseURL": "https://api.berget.ai/v1"
156
111
  },
157
112
  "models": {
158
- "deepseek-r1": {
159
- "name": "GLM-4.6",
113
+ "glm-4.7": {
114
+ "name": "GLM-4.7",
160
115
  "limit": {
161
116
  "output": 4000,
162
117
  "context": 90000
163
118
  }
164
119
  },
120
+
165
121
  "gpt-oss": {
166
122
  "name": "GPT-OSS",
167
123
  "limit": {
168
124
  "output": 4000,
169
125
  "context": 128000
126
+ },
127
+ "modalities": {
128
+ "input": ["text", "image"],
129
+ "output": ["text"]
170
130
  }
171
131
  },
172
132
  "llama-8b": {
@@ -179,4 +139,4 @@
179
139
  }
180
140
  }
181
141
  }
182
- }
142
+ }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "berget",
3
- "version": "2.0.6",
3
+ "version": "2.1.0",
4
4
  "main": "dist/index.js",
5
5
  "bin": {
6
6
  "berget": "dist/index.js"
@@ -42,18 +42,18 @@ export function registerChatCommands(program: Command): void {
42
42
  .command(SUBCOMMANDS.CHAT.RUN)
43
43
  .description('Run a chat session with a specified model')
44
44
  .argument('[message]', 'Message to send directly (skips interactive mode)')
45
- .option('-m, --model <model>', 'Model to use (default: deepseek-r1)')
46
- .option('--no-reasoning', 'Disable reasoning mode (adds </think> to messages)')
45
+ .option('-m, --model <model>', 'Model to use (default: glm-4.7)')
46
+
47
47
  .option('-t, --temperature <temp>', 'Temperature (0-1)', parseFloat)
48
48
  .option('--max-tokens <tokens>', 'Maximum tokens to generate', parseInt)
49
49
  .option('-k, --api-key <key>', 'API key to use for this chat session')
50
50
  .option(
51
51
  '--api-key-id <id>',
52
- 'ID of the API key to use from your saved keys',
52
+ 'ID of the API key to use from your saved keys'
53
53
  )
54
54
  .option(
55
55
  '--no-stream',
56
- 'Disable streaming (streaming is enabled by default)',
56
+ 'Disable streaming (streaming is enabled by default)'
57
57
  )
58
58
  .action(async (message, options) => {
59
59
  try {
@@ -67,7 +67,7 @@ export function registerChatCommands(program: Command): void {
67
67
  const envApiKey = process.env.BERGET_API_KEY
68
68
  if (envApiKey) {
69
69
  console.log(
70
- chalk.dim(`Using API key from BERGET_API_KEY environment variable`),
70
+ chalk.dim(`Using API key from BERGET_API_KEY environment variable`)
71
71
  )
72
72
  apiKey = envApiKey
73
73
 
@@ -75,8 +75,11 @@ export function registerChatCommands(program: Command): void {
75
75
  if (process.argv.includes('--debug')) {
76
76
  console.log(
77
77
  chalk.yellow(
78
- `DEBUG: API key from env starts with: ${envApiKey.substring(0, 4)}...`,
79
- ),
78
+ `DEBUG: API key from env starts with: ${envApiKey.substring(
79
+ 0,
80
+ 4
81
+ )}...`
82
+ )
80
83
  )
81
84
  }
82
85
  }
@@ -98,18 +101,18 @@ export function registerChatCommands(program: Command): void {
98
101
 
99
102
  if (apiKey) {
100
103
  console.log(
101
- chalk.dim(`Using default API key: ${defaultApiKeyData.name}`),
104
+ chalk.dim(`Using default API key: ${defaultApiKeyData.name}`)
102
105
  )
103
106
  } else {
104
107
  console.log(
105
108
  chalk.yellow(
106
- `Default API key "${defaultApiKeyData.name}" exists but the key value is missing.`,
107
- ),
109
+ `Default API key "${defaultApiKeyData.name}" exists but the key value is missing.`
110
+ )
108
111
  )
109
112
  console.log(
110
113
  chalk.yellow(
111
- `Try rotating the key with: berget api-keys rotate ${defaultApiKeyData.id}`,
112
- ),
114
+ `Try rotating the key with: berget api-keys rotate ${defaultApiKeyData.id}`
115
+ )
113
116
  )
114
117
  }
115
118
  } else {
@@ -122,24 +125,24 @@ export function registerChatCommands(program: Command): void {
122
125
  if (!apiKey) {
123
126
  console.log(
124
127
  chalk.red(
125
- 'Error: An API key is required to use the chat command.',
126
- ),
128
+ 'Error: An API key is required to use the chat command.'
129
+ )
127
130
  )
128
131
  console.log(chalk.yellow('You can:'))
129
132
  console.log(
130
133
  chalk.yellow(
131
- '1. Create an API key with: berget api-keys create --name "My Key"',
132
- ),
134
+ '1. Create an API key with: berget api-keys create --name "My Key"'
135
+ )
133
136
  )
134
137
  console.log(
135
138
  chalk.yellow(
136
- '2. Set a default API key with: berget api-keys set-default <id>',
137
- ),
139
+ '2. Set a default API key with: berget api-keys set-default <id>'
140
+ )
138
141
  )
139
142
  console.log(
140
143
  chalk.yellow(
141
- '3. Provide an API key with the --api-key option',
142
- ),
144
+ '3. Provide an API key with the --api-key option'
145
+ )
143
146
  )
144
147
  return
145
148
  }
@@ -147,7 +150,7 @@ export function registerChatCommands(program: Command): void {
147
150
  } catch (error) {
148
151
  if (process.argv.includes('--debug')) {
149
152
  console.log(
150
- chalk.yellow('DEBUG: Error checking default API key:'),
153
+ chalk.yellow('DEBUG: Error checking default API key:')
151
154
  )
152
155
  console.log(chalk.yellow(String(error)))
153
156
  }
@@ -160,14 +163,14 @@ export function registerChatCommands(program: Command): void {
160
163
  const apiKeyService = ApiKeyService.getInstance()
161
164
  const keys = await apiKeyService.list()
162
165
  const selectedKey = keys.find(
163
- (key) => key.id.toString() === options.apiKeyId,
166
+ (key) => key.id.toString() === options.apiKeyId
164
167
  )
165
168
 
166
169
  if (!selectedKey) {
167
170
  console.log(
168
171
  chalk.yellow(
169
- `API key with ID ${options.apiKeyId} not found. Using default authentication.`,
170
- ),
172
+ `API key with ID ${options.apiKeyId} not found. Using default authentication.`
173
+ )
171
174
  )
172
175
  } else {
173
176
  console.log(chalk.dim(`Using API key: ${selectedKey.name}`))
@@ -176,20 +179,20 @@ export function registerChatCommands(program: Command): void {
176
179
  if (
177
180
  await confirm(
178
181
  chalk.yellow(
179
- `To use API key "${selectedKey.name}", it needs to be rotated. This will invalidate the current key. Continue? (y/n)`,
180
- ),
182
+ `To use API key "${selectedKey.name}", it needs to be rotated. This will invalidate the current key. Continue? (y/n)`
183
+ )
181
184
  )
182
185
  ) {
183
186
  const rotatedKey = await apiKeyService.rotate(options.apiKeyId)
184
187
  apiKey = rotatedKey.key
185
188
  console.log(
186
189
  chalk.green(
187
- `API key "${selectedKey.name}" rotated successfully.`,
188
- ),
190
+ `API key "${selectedKey.name}" rotated successfully.`
191
+ )
189
192
  )
190
193
  } else {
191
194
  console.log(
192
- chalk.yellow('Using default authentication instead.'),
195
+ chalk.yellow('Using default authentication instead.')
193
196
  )
194
197
  }
195
198
  }
@@ -205,8 +208,8 @@ export function registerChatCommands(program: Command): void {
205
208
  if (isAuthError) {
206
209
  console.log(
207
210
  chalk.yellow(
208
- 'Authentication required. Please run `berget auth login` first.',
209
- ),
211
+ 'Authentication required. Please run `berget auth login` first.'
212
+ )
210
213
  )
211
214
  } else {
212
215
  console.error(chalk.red('Error fetching API key:'))
@@ -226,12 +229,12 @@ export function registerChatCommands(program: Command): void {
226
229
  console.log(chalk.yellow('1. Log in with `berget auth login`'))
227
230
  console.log(chalk.yellow('2. Provide an API key with `--api-key`'))
228
231
  console.log(
229
- chalk.yellow('3. Provide an API key ID with `--api-key-id`'),
232
+ chalk.yellow('3. Provide an API key ID with `--api-key-id`')
230
233
  )
231
234
  console.log(
232
235
  chalk.yellow(
233
- '4. Set a default API key with `berget api-keys set-default <id>`',
234
- ),
236
+ '4. Set a default API key with `berget api-keys set-default <id>`'
237
+ )
235
238
  )
236
239
  return
237
240
  }
@@ -326,13 +329,14 @@ export function registerChatCommands(program: Command): void {
326
329
 
327
330
  // Fallback to non-streaming if streaming fails
328
331
  console.log(
329
- chalk.yellow('Falling back to non-streaming mode...'),
332
+ chalk.yellow('Falling back to non-streaming mode...')
330
333
  )
331
334
  completionOptions.stream = false
332
335
  delete completionOptions.onChunk
333
336
 
334
- const response =
335
- await chatService.createCompletion(completionOptions)
337
+ const response = await chatService.createCompletion(
338
+ completionOptions
339
+ )
336
340
 
337
341
  if (
338
342
  response &&
@@ -348,8 +352,9 @@ export function registerChatCommands(program: Command): void {
348
352
  return
349
353
  }
350
354
 
351
- const response =
352
- await chatService.createCompletion(completionOptions)
355
+ const response = await chatService.createCompletion(
356
+ completionOptions
357
+ )
353
358
 
354
359
  // Check if response has the expected structure
355
360
  if (
@@ -359,10 +364,10 @@ export function registerChatCommands(program: Command): void {
359
364
  !response.choices[0].message
360
365
  ) {
361
366
  console.error(
362
- chalk.red('Error: Unexpected response format from API'),
367
+ chalk.red('Error: Unexpected response format from API')
363
368
  )
364
369
  console.error(
365
- chalk.red('Response:', JSON.stringify(response, null, 2)),
370
+ chalk.red('Response:', JSON.stringify(response, null, 2))
366
371
  )
367
372
  throw new Error('Unexpected response format from API')
368
373
  }
@@ -463,13 +468,14 @@ export function registerChatCommands(program: Command): void {
463
468
 
464
469
  // Fallback to non-streaming if streaming fails
465
470
  console.log(
466
- chalk.yellow('Falling back to non-streaming mode...'),
471
+ chalk.yellow('Falling back to non-streaming mode...')
467
472
  )
468
473
  completionOptions.stream = false
469
474
  delete completionOptions.onChunk
470
475
 
471
- const response =
472
- await chatService.createCompletion(completionOptions)
476
+ const response = await chatService.createCompletion(
477
+ completionOptions
478
+ )
473
479
 
474
480
  if (
475
481
  response &&
@@ -494,8 +500,9 @@ export function registerChatCommands(program: Command): void {
494
500
  return
495
501
  }
496
502
 
497
- const response =
498
- await chatService.createCompletion(completionOptions)
503
+ const response = await chatService.createCompletion(
504
+ completionOptions
505
+ )
499
506
 
500
507
  // Debug output
501
508
  if (program.opts().debug) {
@@ -511,10 +518,10 @@ export function registerChatCommands(program: Command): void {
511
518
  !response.choices[0].message
512
519
  ) {
513
520
  console.error(
514
- chalk.red('Error: Unexpected response format from API'),
521
+ chalk.red('Error: Unexpected response format from API')
515
522
  )
516
523
  console.error(
517
- chalk.red('Response:', JSON.stringify(response, null, 2)),
524
+ chalk.red('Response:', JSON.stringify(response, null, 2))
518
525
  )
519
526
  throw new Error('Unexpected response format from API')
520
527
  }
@@ -566,7 +573,7 @@ export function registerChatCommands(program: Command): void {
566
573
  .option('-k, --api-key <key>', 'API key to use for this request')
567
574
  .option(
568
575
  '--api-key-id <id>',
569
- 'ID of the API key to use from your saved keys',
576
+ 'ID of the API key to use from your saved keys'
570
577
  )
571
578
  .action(async (options) => {
572
579
  try {
@@ -582,7 +589,7 @@ export function registerChatCommands(program: Command): void {
582
589
  if (defaultApiKeyData) {
583
590
  apiKeyId = defaultApiKeyData.id
584
591
  console.log(
585
- chalk.dim(`Using default API key: ${defaultApiKeyData.name}`),
592
+ chalk.dim(`Using default API key: ${defaultApiKeyData.name}`)
586
593
  )
587
594
  }
588
595
  }
@@ -592,14 +599,14 @@ export function registerChatCommands(program: Command): void {
592
599
  const apiKeyService = ApiKeyService.getInstance()
593
600
  const keys = await apiKeyService.list()
594
601
  const selectedKey = keys.find(
595
- (key) => key.id.toString() === options.apiKeyId,
602
+ (key) => key.id.toString() === options.apiKeyId
596
603
  )
597
604
 
598
605
  if (!selectedKey) {
599
606
  console.log(
600
607
  chalk.yellow(
601
- `API key with ID ${options.apiKeyId} not found. Using default authentication.`,
602
- ),
608
+ `API key with ID ${options.apiKeyId} not found. Using default authentication.`
609
+ )
603
610
  )
604
611
  } else {
605
612
  console.log(chalk.dim(`Using API key: ${selectedKey.name}`))
@@ -608,20 +615,20 @@ export function registerChatCommands(program: Command): void {
608
615
  if (
609
616
  await confirm(
610
617
  chalk.yellow(
611
- `To use API key "${selectedKey.name}", it needs to be rotated. This will invalidate the current key. Continue? (y/n)`,
612
- ),
618
+ `To use API key "${selectedKey.name}", it needs to be rotated. This will invalidate the current key. Continue? (y/n)`
619
+ )
613
620
  )
614
621
  ) {
615
622
  const rotatedKey = await apiKeyService.rotate(options.apiKeyId)
616
623
  apiKey = rotatedKey.key
617
624
  console.log(
618
625
  chalk.green(
619
- `API key "${selectedKey.name}" rotated successfully.`,
620
- ),
626
+ `API key "${selectedKey.name}" rotated successfully.`
627
+ )
621
628
  )
622
629
  } else {
623
630
  console.log(
624
- chalk.yellow('Using default authentication instead.'),
631
+ chalk.yellow('Using default authentication instead.')
625
632
  )
626
633
  }
627
634
  }
@@ -644,13 +651,13 @@ export function registerChatCommands(program: Command): void {
644
651
  console.log(chalk.bold('Available Chat Models:'))
645
652
  console.log(chalk.dim('─'.repeat(70)))
646
653
  console.log(
647
- chalk.dim('MODEL ID'.padEnd(40)) + chalk.dim('CAPABILITIES'),
654
+ chalk.dim('MODEL ID'.padEnd(40)) + chalk.dim('CAPABILITIES')
648
655
  )
649
656
  console.log(chalk.dim('─'.repeat(70)))
650
657
 
651
658
  // Filter to only show active models
652
659
  const activeModels = models.data.filter(
653
- (model: any) => model.active === true,
660
+ (model: any) => model.active === true
654
661
  )
655
662
 
656
663
  activeModels.forEach((model: any) => {
@@ -662,7 +669,7 @@ export function registerChatCommands(program: Command): void {
662
669
 
663
670
  // Format model ID in Huggingface compatible format (owner/model)
664
671
  const modelId = `${model.owned_by.toLowerCase()}/${model.id}`.padEnd(
665
- 40,
672
+ 40
666
673
  )
667
674
 
668
675
  console.log(modelId + capabilities.join(', '))