genbox 1.0.129 → 1.0.130
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/dist/commands/completion.js +635 -0
- package/dist/commands/list.js +16 -9
- package/dist/commands/login.js +7 -1
- package/dist/index.js +131 -12
- package/package.json +1 -1
|
@@ -0,0 +1,635 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
|
3
|
+
if (k2 === undefined) k2 = k;
|
|
4
|
+
var desc = Object.getOwnPropertyDescriptor(m, k);
|
|
5
|
+
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
|
6
|
+
desc = { enumerable: true, get: function() { return m[k]; } };
|
|
7
|
+
}
|
|
8
|
+
Object.defineProperty(o, k2, desc);
|
|
9
|
+
}) : (function(o, m, k, k2) {
|
|
10
|
+
if (k2 === undefined) k2 = k;
|
|
11
|
+
o[k2] = m[k];
|
|
12
|
+
}));
|
|
13
|
+
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
|
|
14
|
+
Object.defineProperty(o, "default", { enumerable: true, value: v });
|
|
15
|
+
}) : function(o, v) {
|
|
16
|
+
o["default"] = v;
|
|
17
|
+
});
|
|
18
|
+
var __importStar = (this && this.__importStar) || (function () {
|
|
19
|
+
var ownKeys = function(o) {
|
|
20
|
+
ownKeys = Object.getOwnPropertyNames || function (o) {
|
|
21
|
+
var ar = [];
|
|
22
|
+
for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
|
|
23
|
+
return ar;
|
|
24
|
+
};
|
|
25
|
+
return ownKeys(o);
|
|
26
|
+
};
|
|
27
|
+
return function (mod) {
|
|
28
|
+
if (mod && mod.__esModule) return mod;
|
|
29
|
+
var result = {};
|
|
30
|
+
if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
|
|
31
|
+
__setModuleDefault(result, mod);
|
|
32
|
+
return result;
|
|
33
|
+
};
|
|
34
|
+
})();
|
|
35
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
36
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
37
|
+
};
|
|
38
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
39
|
+
exports.completionCommand = void 0;
|
|
40
|
+
exports.isCompletionInstalledForCurrentShell = isCompletionInstalledForCurrentShell;
|
|
41
|
+
exports.getCompletionHint = getCompletionHint;
|
|
42
|
+
const commander_1 = require("commander");
|
|
43
|
+
const chalk_1 = __importDefault(require("chalk"));
|
|
44
|
+
const os = __importStar(require("os"));
|
|
45
|
+
const path = __importStar(require("path"));
|
|
46
|
+
const fs = __importStar(require("fs"));
|
|
47
|
+
// Get all command names for completion
|
|
48
|
+
const commands = [
|
|
49
|
+
'init', 'create', 'list', 'ls', 'destroy', 'delete', 'connect', 'balance',
|
|
50
|
+
'login', 'urls', 'push', 'status', 'forward', 'restore-db', 'help',
|
|
51
|
+
'profiles', 'db', 'config', 'resolve', 'validate', 'rebuild', 'extend',
|
|
52
|
+
'cleanup-ssh', 'restart', 'backup', 'backups', 'stop', 'start', 'resume',
|
|
53
|
+
'template', 'run-prompt', 'run', 'completion'
|
|
54
|
+
];
|
|
55
|
+
// Marker comment to identify our completion setup
|
|
56
|
+
const COMPLETION_MARKER = '# Genbox CLI completion';
|
|
57
|
+
function getShellConfig(shell) {
|
|
58
|
+
const home = os.homedir();
|
|
59
|
+
switch (shell) {
|
|
60
|
+
case 'bash':
|
|
61
|
+
// Check for .bashrc first, then .bash_profile (macOS default)
|
|
62
|
+
const bashrc = path.join(home, '.bashrc');
|
|
63
|
+
const bashProfile = path.join(home, '.bash_profile');
|
|
64
|
+
const configFile = fs.existsSync(bashrc) ? bashrc : bashProfile;
|
|
65
|
+
return {
|
|
66
|
+
configFile,
|
|
67
|
+
evalCommand: 'eval "$(gb completion bash)"',
|
|
68
|
+
reloadCommand: `source ${configFile}`,
|
|
69
|
+
};
|
|
70
|
+
case 'zsh':
|
|
71
|
+
return {
|
|
72
|
+
configFile: path.join(home, '.zshrc'),
|
|
73
|
+
evalCommand: 'eval "$(gb completion zsh)"',
|
|
74
|
+
reloadCommand: 'source ~/.zshrc',
|
|
75
|
+
};
|
|
76
|
+
case 'fish':
|
|
77
|
+
const fishCompletionsDir = path.join(home, '.config', 'fish', 'completions');
|
|
78
|
+
return {
|
|
79
|
+
configFile: path.join(fishCompletionsDir, 'gb.fish'),
|
|
80
|
+
evalCommand: '', // Fish doesn't use eval, we write directly to completions file
|
|
81
|
+
reloadCommand: '', // Fish auto-loads from completions directory
|
|
82
|
+
};
|
|
83
|
+
default:
|
|
84
|
+
return null;
|
|
85
|
+
}
|
|
86
|
+
}
|
|
87
|
+
function isCompletionInstalled(shell, config) {
|
|
88
|
+
if (shell === 'fish') {
|
|
89
|
+
// For fish, check if the completions file exists
|
|
90
|
+
return fs.existsSync(config.configFile);
|
|
91
|
+
}
|
|
92
|
+
// For bash/zsh, check if the config file contains our completion command
|
|
93
|
+
if (!fs.existsSync(config.configFile)) {
|
|
94
|
+
return false;
|
|
95
|
+
}
|
|
96
|
+
const content = fs.readFileSync(config.configFile, 'utf8');
|
|
97
|
+
return content.includes('gb completion') || content.includes(COMPLETION_MARKER);
|
|
98
|
+
}
|
|
99
|
+
function installCompletion(shell, config) {
|
|
100
|
+
try {
|
|
101
|
+
if (shell === 'fish') {
|
|
102
|
+
// For fish, create the completions directory if needed and write the file
|
|
103
|
+
const fishDir = path.dirname(config.configFile);
|
|
104
|
+
if (!fs.existsSync(fishDir)) {
|
|
105
|
+
fs.mkdirSync(fishDir, { recursive: true });
|
|
106
|
+
}
|
|
107
|
+
fs.writeFileSync(config.configFile, generateFishCompletion());
|
|
108
|
+
return {
|
|
109
|
+
success: true,
|
|
110
|
+
message: `Completions installed to ${config.configFile}`,
|
|
111
|
+
};
|
|
112
|
+
}
|
|
113
|
+
// For bash/zsh, append to config file
|
|
114
|
+
const completionBlock = `
|
|
115
|
+
${COMPLETION_MARKER}
|
|
116
|
+
${config.evalCommand}
|
|
117
|
+
`;
|
|
118
|
+
// Create config file if it doesn't exist
|
|
119
|
+
if (!fs.existsSync(config.configFile)) {
|
|
120
|
+
fs.writeFileSync(config.configFile, completionBlock);
|
|
121
|
+
}
|
|
122
|
+
else {
|
|
123
|
+
fs.appendFileSync(config.configFile, completionBlock);
|
|
124
|
+
}
|
|
125
|
+
return {
|
|
126
|
+
success: true,
|
|
127
|
+
message: `Completions added to ${config.configFile}`,
|
|
128
|
+
};
|
|
129
|
+
}
|
|
130
|
+
catch (error) {
|
|
131
|
+
return {
|
|
132
|
+
success: false,
|
|
133
|
+
message: error.message,
|
|
134
|
+
};
|
|
135
|
+
}
|
|
136
|
+
}
|
|
137
|
+
function generateBashCompletion() {
|
|
138
|
+
return `# Bash completion for genbox/gb
|
|
139
|
+
# Add to ~/.bashrc or ~/.bash_profile:
|
|
140
|
+
# eval "$(gb completion bash)"
|
|
141
|
+
# Or save to a file:
|
|
142
|
+
# gb completion bash > /etc/bash_completion.d/gb
|
|
143
|
+
|
|
144
|
+
_genbox_completions() {
|
|
145
|
+
local cur prev commands
|
|
146
|
+
COMPREPLY=()
|
|
147
|
+
cur="\${COMP_WORDS[COMP_CWORD]}"
|
|
148
|
+
prev="\${COMP_WORDS[COMP_CWORD-1]}"
|
|
149
|
+
|
|
150
|
+
# Main commands
|
|
151
|
+
commands="${commands.join(' ')}"
|
|
152
|
+
|
|
153
|
+
# Subcommands for grouped commands
|
|
154
|
+
local db_commands="sync restore snapshots"
|
|
155
|
+
local config_commands="show diff"
|
|
156
|
+
local template_commands="build list status delete"
|
|
157
|
+
local profiles_commands="list"
|
|
158
|
+
local backups_commands="list restore delete"
|
|
159
|
+
|
|
160
|
+
case "\${prev}" in
|
|
161
|
+
genbox|gb)
|
|
162
|
+
COMPREPLY=( $(compgen -W "\${commands}" -- "\${cur}") )
|
|
163
|
+
return 0
|
|
164
|
+
;;
|
|
165
|
+
db)
|
|
166
|
+
COMPREPLY=( $(compgen -W "\${db_commands}" -- "\${cur}") )
|
|
167
|
+
return 0
|
|
168
|
+
;;
|
|
169
|
+
config)
|
|
170
|
+
COMPREPLY=( $(compgen -W "\${config_commands}" -- "\${cur}") )
|
|
171
|
+
return 0
|
|
172
|
+
;;
|
|
173
|
+
template)
|
|
174
|
+
COMPREPLY=( $(compgen -W "\${template_commands}" -- "\${cur}") )
|
|
175
|
+
return 0
|
|
176
|
+
;;
|
|
177
|
+
profiles)
|
|
178
|
+
COMPREPLY=( $(compgen -W "\${profiles_commands}" -- "\${cur}") )
|
|
179
|
+
return 0
|
|
180
|
+
;;
|
|
181
|
+
backups)
|
|
182
|
+
COMPREPLY=( $(compgen -W "\${backups_commands}" -- "\${cur}") )
|
|
183
|
+
return 0
|
|
184
|
+
;;
|
|
185
|
+
completion)
|
|
186
|
+
COMPREPLY=( $(compgen -W "bash zsh fish --install" -- "\${cur}") )
|
|
187
|
+
return 0
|
|
188
|
+
;;
|
|
189
|
+
# Commands that take genbox names - could be enhanced with dynamic completion
|
|
190
|
+
create|destroy|delete|connect|status|urls|forward|push|restart|stop|start|resume|extend|rebuild|run|run-prompt)
|
|
191
|
+
# For now, no completion for genbox names (would need API call)
|
|
192
|
+
return 0
|
|
193
|
+
;;
|
|
194
|
+
-s|--size)
|
|
195
|
+
COMPREPLY=( $(compgen -W "small medium large xl" -- "\${cur}") )
|
|
196
|
+
return 0
|
|
197
|
+
;;
|
|
198
|
+
-p|--profile)
|
|
199
|
+
# Profile names would need to be read from config
|
|
200
|
+
return 0
|
|
201
|
+
;;
|
|
202
|
+
--db)
|
|
203
|
+
COMPREPLY=( $(compgen -W "none fresh copy remote" -- "\${cur}") )
|
|
204
|
+
return 0
|
|
205
|
+
;;
|
|
206
|
+
--db-source)
|
|
207
|
+
COMPREPLY=( $(compgen -W "staging production" -- "\${cur}") )
|
|
208
|
+
return 0
|
|
209
|
+
;;
|
|
210
|
+
esac
|
|
211
|
+
|
|
212
|
+
# Option completion
|
|
213
|
+
if [[ "\${cur}" == -* ]]; then
|
|
214
|
+
local opts="--help -h"
|
|
215
|
+
case "\${COMP_WORDS[1]}" in
|
|
216
|
+
create)
|
|
217
|
+
opts="--help -h --profile -p --apps -a --add-apps --api --db --db-source --db-dump --db-copy-remote --size -s --branch -b --new-branch -n --from-branch -f --yes -y --dry-run --restore -r --inject-claude-auth"
|
|
218
|
+
;;
|
|
219
|
+
list|ls)
|
|
220
|
+
opts="--help -h --all -a --terminated"
|
|
221
|
+
;;
|
|
222
|
+
destroy|delete)
|
|
223
|
+
opts="--help -h --yes -y --all -a --save-changes"
|
|
224
|
+
;;
|
|
225
|
+
status)
|
|
226
|
+
opts="--help -h --all -a --watch -w"
|
|
227
|
+
;;
|
|
228
|
+
connect)
|
|
229
|
+
opts="--help -h --all -a"
|
|
230
|
+
;;
|
|
231
|
+
forward)
|
|
232
|
+
opts="--help -h --ports -p --all -a"
|
|
233
|
+
;;
|
|
234
|
+
extend)
|
|
235
|
+
opts="--help -h --hours --disable-auto-destroy --enable-auto-destroy --all -a"
|
|
236
|
+
;;
|
|
237
|
+
rebuild)
|
|
238
|
+
opts="--help -h --yes -y --all -a"
|
|
239
|
+
;;
|
|
240
|
+
stop)
|
|
241
|
+
opts="--help -h --yes -y --all -a"
|
|
242
|
+
;;
|
|
243
|
+
start|resume)
|
|
244
|
+
opts="--help -h --all -a"
|
|
245
|
+
;;
|
|
246
|
+
completion)
|
|
247
|
+
opts="--help -h --install"
|
|
248
|
+
;;
|
|
249
|
+
esac
|
|
250
|
+
COMPREPLY=( $(compgen -W "\${opts}" -- "\${cur}") )
|
|
251
|
+
return 0
|
|
252
|
+
fi
|
|
253
|
+
}
|
|
254
|
+
|
|
255
|
+
complete -F _genbox_completions genbox
|
|
256
|
+
complete -F _genbox_completions gb
|
|
257
|
+
`;
|
|
258
|
+
}
|
|
259
|
+
function generateZshCompletion() {
|
|
260
|
+
return `#compdef genbox gb
|
|
261
|
+
# Zsh completion for genbox/gb
|
|
262
|
+
# Add to ~/.zshrc:
|
|
263
|
+
# eval "$(gb completion zsh)"
|
|
264
|
+
# Or save to a file in your fpath:
|
|
265
|
+
# gb completion zsh > ~/.zsh/completions/_gb
|
|
266
|
+
|
|
267
|
+
_genbox() {
|
|
268
|
+
local -a commands
|
|
269
|
+
commands=(
|
|
270
|
+
'init:Initialize genbox.yaml configuration'
|
|
271
|
+
'create:Create a new Genbox environment'
|
|
272
|
+
'list:List genboxes'
|
|
273
|
+
'ls:List genboxes (alias)'
|
|
274
|
+
'destroy:Destroy a Genbox'
|
|
275
|
+
'delete:Destroy a Genbox (alias)'
|
|
276
|
+
'connect:SSH into a Genbox'
|
|
277
|
+
'status:Check Genbox status'
|
|
278
|
+
'urls:Show service URLs'
|
|
279
|
+
'forward:Set up port forwarding'
|
|
280
|
+
'push:Push local changes'
|
|
281
|
+
'restore-db:Restore database to Genbox'
|
|
282
|
+
'balance:Show credit balance'
|
|
283
|
+
'login:Authenticate with Genbox'
|
|
284
|
+
'help:Show detailed help'
|
|
285
|
+
'profiles:Manage profiles'
|
|
286
|
+
'db:Database operations'
|
|
287
|
+
'config:Configuration commands'
|
|
288
|
+
'template:Manage templates'
|
|
289
|
+
'rebuild:Rebuild a Genbox'
|
|
290
|
+
'extend:Extend Genbox lifetime'
|
|
291
|
+
'restart:Restart services'
|
|
292
|
+
'stop:Stop a Genbox'
|
|
293
|
+
'start:Start a stopped Genbox'
|
|
294
|
+
'resume:Start a stopped Genbox (alias)'
|
|
295
|
+
'backup:Create a backup'
|
|
296
|
+
'backups:Manage backups'
|
|
297
|
+
'cleanup-ssh:Clean up SSH config'
|
|
298
|
+
'run-prompt:Run Claude Code prompt'
|
|
299
|
+
'run:Run Claude Code prompt (alias)'
|
|
300
|
+
'completion:Generate shell completions'
|
|
301
|
+
)
|
|
302
|
+
|
|
303
|
+
local -a db_commands
|
|
304
|
+
db_commands=(
|
|
305
|
+
'sync:Sync database from staging/production'
|
|
306
|
+
'restore:Restore from snapshot'
|
|
307
|
+
'snapshots:List snapshots'
|
|
308
|
+
)
|
|
309
|
+
|
|
310
|
+
local -a config_commands
|
|
311
|
+
config_commands=(
|
|
312
|
+
'show:Show configuration'
|
|
313
|
+
'diff:Compare profiles'
|
|
314
|
+
)
|
|
315
|
+
|
|
316
|
+
local -a template_commands
|
|
317
|
+
template_commands=(
|
|
318
|
+
'build:Build a template'
|
|
319
|
+
'list:List templates'
|
|
320
|
+
'status:Check template status'
|
|
321
|
+
'delete:Delete a template'
|
|
322
|
+
)
|
|
323
|
+
|
|
324
|
+
local -a sizes
|
|
325
|
+
sizes=('small' 'medium' 'large' 'xl')
|
|
326
|
+
|
|
327
|
+
local -a db_modes
|
|
328
|
+
db_modes=('none' 'fresh' 'copy' 'remote')
|
|
329
|
+
|
|
330
|
+
local -a db_sources
|
|
331
|
+
db_sources=('staging' 'production')
|
|
332
|
+
|
|
333
|
+
_arguments -C \\
|
|
334
|
+
'(-h --help)'{-h,--help}'[Show help]' \\
|
|
335
|
+
'(-v --version)'{-v,--version}'[Show version]' \\
|
|
336
|
+
'1: :->command' \\
|
|
337
|
+
'*:: :->args'
|
|
338
|
+
|
|
339
|
+
case $state in
|
|
340
|
+
command)
|
|
341
|
+
_describe -t commands 'genbox command' commands
|
|
342
|
+
;;
|
|
343
|
+
args)
|
|
344
|
+
case $words[1] in
|
|
345
|
+
db)
|
|
346
|
+
_describe -t commands 'db command' db_commands
|
|
347
|
+
;;
|
|
348
|
+
config)
|
|
349
|
+
_describe -t commands 'config command' config_commands
|
|
350
|
+
;;
|
|
351
|
+
template)
|
|
352
|
+
_describe -t commands 'template command' template_commands
|
|
353
|
+
;;
|
|
354
|
+
completion)
|
|
355
|
+
_arguments \\
|
|
356
|
+
'--install[Install completions to shell config]' \\
|
|
357
|
+
'1:shell:(bash zsh fish)'
|
|
358
|
+
;;
|
|
359
|
+
create)
|
|
360
|
+
_arguments \\
|
|
361
|
+
'(-p --profile)'{-p,--profile}'[Use profile]:profile:' \\
|
|
362
|
+
'(-a --apps)'{-a,--apps}'[Apps to include]:apps:' \\
|
|
363
|
+
'--add-apps[Add apps to profile]:apps:' \\
|
|
364
|
+
'--api[API mode]:mode:(local staging production)' \\
|
|
365
|
+
'--db[Database mode]:mode:(none fresh copy remote)' \\
|
|
366
|
+
'--db-source[Database source]:source:(staging production)' \\
|
|
367
|
+
'--db-dump[Use existing dump]:file:_files' \\
|
|
368
|
+
'--db-copy-remote[Copy database on server]' \\
|
|
369
|
+
'(-s --size)'{-s,--size}'[Server size]:size:(small medium large xl)' \\
|
|
370
|
+
'(-b --branch)'{-b,--branch}'[Use existing branch]:branch:' \\
|
|
371
|
+
'(-n --new-branch)'{-n,--new-branch}'[Create new branch]:name:' \\
|
|
372
|
+
'(-f --from-branch)'{-f,--from-branch}'[Source branch]:branch:' \\
|
|
373
|
+
'(-y --yes)'{-y,--yes}'[Skip prompts]' \\
|
|
374
|
+
'--dry-run[Show what would be created]' \\
|
|
375
|
+
'(-r --restore)'{-r,--restore}'[Restore from backup]' \\
|
|
376
|
+
'--inject-claude-auth[Inject Claude credentials]' \\
|
|
377
|
+
'1:name:'
|
|
378
|
+
;;
|
|
379
|
+
list|ls)
|
|
380
|
+
_arguments \\
|
|
381
|
+
'(-a --all)'{-a,--all}'[Show all genboxes]' \\
|
|
382
|
+
'--terminated[Include terminated]'
|
|
383
|
+
;;
|
|
384
|
+
destroy|delete)
|
|
385
|
+
_arguments \\
|
|
386
|
+
'(-y --yes)'{-y,--yes}'[Skip confirmation]' \\
|
|
387
|
+
'(-a --all)'{-a,--all}'[Bulk delete mode]' \\
|
|
388
|
+
'--save-changes[Handle changes]:action:(save trash skip)' \\
|
|
389
|
+
'1:name:'
|
|
390
|
+
;;
|
|
391
|
+
status)
|
|
392
|
+
_arguments \\
|
|
393
|
+
'(-a --all)'{-a,--all}'[Select from all]' \\
|
|
394
|
+
'(-w --watch)'{-w,--watch}'[Watch mode]' \\
|
|
395
|
+
'1:name:'
|
|
396
|
+
;;
|
|
397
|
+
connect|urls|restart|stop)
|
|
398
|
+
_arguments \\
|
|
399
|
+
'(-a --all)'{-a,--all}'[Select from all]' \\
|
|
400
|
+
'1:name:'
|
|
401
|
+
;;
|
|
402
|
+
start|resume)
|
|
403
|
+
_arguments \\
|
|
404
|
+
'(-a --all)'{-a,--all}'[Select from all]' \\
|
|
405
|
+
'1:name:'
|
|
406
|
+
;;
|
|
407
|
+
forward)
|
|
408
|
+
_arguments \\
|
|
409
|
+
'(-a --all)'{-a,--all}'[Select from all]' \\
|
|
410
|
+
'(-p --ports)'{-p,--ports}'[Additional ports]:ports:' \\
|
|
411
|
+
'1:name:'
|
|
412
|
+
;;
|
|
413
|
+
extend)
|
|
414
|
+
_arguments \\
|
|
415
|
+
'(-a --all)'{-a,--all}'[Select from all]' \\
|
|
416
|
+
'--hours[Hours to extend]:hours:' \\
|
|
417
|
+
'--disable-auto-destroy[Disable auto-destroy]' \\
|
|
418
|
+
'--enable-auto-destroy[Enable auto-destroy]' \\
|
|
419
|
+
'1:name:'
|
|
420
|
+
;;
|
|
421
|
+
rebuild)
|
|
422
|
+
_arguments \\
|
|
423
|
+
'(-a --all)'{-a,--all}'[Select from all]' \\
|
|
424
|
+
'(-y --yes)'{-y,--yes}'[Skip confirmation]' \\
|
|
425
|
+
'1:name:'
|
|
426
|
+
;;
|
|
427
|
+
help)
|
|
428
|
+
_values 'command' init create status connect forward restore-db urls push destroy
|
|
429
|
+
;;
|
|
430
|
+
esac
|
|
431
|
+
;;
|
|
432
|
+
esac
|
|
433
|
+
}
|
|
434
|
+
|
|
435
|
+
compdef _genbox genbox gb
|
|
436
|
+
`;
|
|
437
|
+
}
|
|
438
|
+
function generateFishCompletion() {
|
|
439
|
+
return `# Fish completion for genbox/gb
|
|
440
|
+
# Save to ~/.config/fish/completions/gb.fish:
|
|
441
|
+
# gb completion fish > ~/.config/fish/completions/gb.fish
|
|
442
|
+
# Or install automatically:
|
|
443
|
+
# gb completion fish --install
|
|
444
|
+
|
|
445
|
+
# Disable file completion by default
|
|
446
|
+
complete -c genbox -f
|
|
447
|
+
complete -c gb -f
|
|
448
|
+
|
|
449
|
+
# Main commands
|
|
450
|
+
complete -c genbox -c gb -n "__fish_use_subcommand" -a "init" -d "Initialize genbox.yaml configuration"
|
|
451
|
+
complete -c genbox -c gb -n "__fish_use_subcommand" -a "create" -d "Create a new Genbox environment"
|
|
452
|
+
complete -c genbox -c gb -n "__fish_use_subcommand" -a "list ls" -d "List genboxes"
|
|
453
|
+
complete -c genbox -c gb -n "__fish_use_subcommand" -a "destroy delete" -d "Destroy a Genbox"
|
|
454
|
+
complete -c genbox -c gb -n "__fish_use_subcommand" -a "connect" -d "SSH into a Genbox"
|
|
455
|
+
complete -c genbox -c gb -n "__fish_use_subcommand" -a "status" -d "Check Genbox status"
|
|
456
|
+
complete -c genbox -c gb -n "__fish_use_subcommand" -a "urls" -d "Show service URLs"
|
|
457
|
+
complete -c genbox -c gb -n "__fish_use_subcommand" -a "forward" -d "Set up port forwarding"
|
|
458
|
+
complete -c genbox -c gb -n "__fish_use_subcommand" -a "push" -d "Push local changes"
|
|
459
|
+
complete -c genbox -c gb -n "__fish_use_subcommand" -a "restore-db" -d "Restore database"
|
|
460
|
+
complete -c genbox -c gb -n "__fish_use_subcommand" -a "balance" -d "Show credit balance"
|
|
461
|
+
complete -c genbox -c gb -n "__fish_use_subcommand" -a "login" -d "Authenticate"
|
|
462
|
+
complete -c genbox -c gb -n "__fish_use_subcommand" -a "help" -d "Show detailed help"
|
|
463
|
+
complete -c genbox -c gb -n "__fish_use_subcommand" -a "profiles" -d "Manage profiles"
|
|
464
|
+
complete -c genbox -c gb -n "__fish_use_subcommand" -a "db" -d "Database operations"
|
|
465
|
+
complete -c genbox -c gb -n "__fish_use_subcommand" -a "config" -d "Configuration commands"
|
|
466
|
+
complete -c genbox -c gb -n "__fish_use_subcommand" -a "template" -d "Manage templates"
|
|
467
|
+
complete -c genbox -c gb -n "__fish_use_subcommand" -a "rebuild" -d "Rebuild a Genbox"
|
|
468
|
+
complete -c genbox -c gb -n "__fish_use_subcommand" -a "extend" -d "Extend Genbox lifetime"
|
|
469
|
+
complete -c genbox -c gb -n "__fish_use_subcommand" -a "restart" -d "Restart services"
|
|
470
|
+
complete -c genbox -c gb -n "__fish_use_subcommand" -a "stop" -d "Stop a Genbox"
|
|
471
|
+
complete -c genbox -c gb -n "__fish_use_subcommand" -a "start resume" -d "Start a stopped Genbox"
|
|
472
|
+
complete -c genbox -c gb -n "__fish_use_subcommand" -a "backup" -d "Create a backup"
|
|
473
|
+
complete -c genbox -c gb -n "__fish_use_subcommand" -a "backups" -d "Manage backups"
|
|
474
|
+
complete -c genbox -c gb -n "__fish_use_subcommand" -a "cleanup-ssh" -d "Clean up SSH config"
|
|
475
|
+
complete -c genbox -c gb -n "__fish_use_subcommand" -a "run-prompt run" -d "Run Claude Code prompt"
|
|
476
|
+
complete -c genbox -c gb -n "__fish_use_subcommand" -a "completion" -d "Generate shell completions"
|
|
477
|
+
|
|
478
|
+
# Subcommands for db
|
|
479
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from db" -a "sync" -d "Sync database"
|
|
480
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from db" -a "restore" -d "Restore from snapshot"
|
|
481
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from db" -a "snapshots" -d "List snapshots"
|
|
482
|
+
|
|
483
|
+
# Subcommands for config
|
|
484
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from config" -a "show" -d "Show configuration"
|
|
485
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from config" -a "diff" -d "Compare profiles"
|
|
486
|
+
|
|
487
|
+
# Subcommands for template
|
|
488
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from template" -a "build" -d "Build template"
|
|
489
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from template" -a "list" -d "List templates"
|
|
490
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from template" -a "status" -d "Check status"
|
|
491
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from template" -a "delete" -d "Delete template"
|
|
492
|
+
|
|
493
|
+
# Subcommands for completion
|
|
494
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from completion" -a "bash" -d "Bash completion"
|
|
495
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from completion" -a "zsh" -d "Zsh completion"
|
|
496
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from completion" -a "fish" -d "Fish completion"
|
|
497
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from completion" -l install -d "Install completions"
|
|
498
|
+
|
|
499
|
+
# Options for create
|
|
500
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from create" -s p -l profile -d "Use profile"
|
|
501
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from create" -s a -l apps -d "Apps to include"
|
|
502
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from create" -l add-apps -d "Add apps to profile"
|
|
503
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from create" -l api -d "API mode" -a "local staging production"
|
|
504
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from create" -l db -d "Database mode" -a "none fresh copy remote"
|
|
505
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from create" -l db-source -d "Database source" -a "staging production"
|
|
506
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from create" -l db-dump -d "Use existing dump" -r
|
|
507
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from create" -l db-copy-remote -d "Copy database on server"
|
|
508
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from create" -s s -l size -d "Server size" -a "small medium large xl"
|
|
509
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from create" -s b -l branch -d "Use existing branch"
|
|
510
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from create" -s n -l new-branch -d "Create new branch"
|
|
511
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from create" -s f -l from-branch -d "Source branch"
|
|
512
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from create" -s y -l yes -d "Skip prompts"
|
|
513
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from create" -l dry-run -d "Show what would be created"
|
|
514
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from create" -s r -l restore -d "Restore from backup"
|
|
515
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from create" -l inject-claude-auth -d "Inject Claude credentials"
|
|
516
|
+
|
|
517
|
+
# Options for list
|
|
518
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from list ls" -s a -l all -d "Show all genboxes"
|
|
519
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from list ls" -l terminated -d "Include terminated"
|
|
520
|
+
|
|
521
|
+
# Options for destroy
|
|
522
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from destroy delete" -s y -l yes -d "Skip confirmation"
|
|
523
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from destroy delete" -s a -l all -d "Bulk delete mode"
|
|
524
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from destroy delete" -l save-changes -d "Handle changes" -a "save trash skip"
|
|
525
|
+
|
|
526
|
+
# Options for status
|
|
527
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from status" -s a -l all -d "Select from all"
|
|
528
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from status" -s w -l watch -d "Watch mode"
|
|
529
|
+
|
|
530
|
+
# Options for extend
|
|
531
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from extend" -s a -l all -d "Select from all"
|
|
532
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from extend" -l hours -d "Hours to extend"
|
|
533
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from extend" -l disable-auto-destroy -d "Disable auto-destroy"
|
|
534
|
+
complete -c genbox -c gb -n "__fish_seen_subcommand_from extend" -l enable-auto-destroy -d "Enable auto-destroy"
|
|
535
|
+
|
|
536
|
+
# Global options
|
|
537
|
+
complete -c genbox -c gb -s h -l help -d "Show help"
|
|
538
|
+
complete -c genbox -c gb -s v -l version -d "Show version"
|
|
539
|
+
`;
|
|
540
|
+
}
|
|
541
|
+
exports.completionCommand = new commander_1.Command('completion')
|
|
542
|
+
.description('Generate shell completion scripts')
|
|
543
|
+
.argument('<shell>', 'Shell type: bash, zsh, or fish')
|
|
544
|
+
.option('--install', 'Install completions to your shell config file')
|
|
545
|
+
.addHelpText('after', `
|
|
546
|
+
Examples:
|
|
547
|
+
${chalk_1.default.dim('# Generate and manually add to config')}
|
|
548
|
+
${chalk_1.default.cyan('eval "$(gb completion bash)"')} ${chalk_1.default.dim('# Add to ~/.bashrc')}
|
|
549
|
+
${chalk_1.default.cyan('eval "$(gb completion zsh)"')} ${chalk_1.default.dim('# Add to ~/.zshrc')}
|
|
550
|
+
|
|
551
|
+
${chalk_1.default.dim('# Auto-install to shell config')}
|
|
552
|
+
${chalk_1.default.cyan('gb completion bash --install')}
|
|
553
|
+
${chalk_1.default.cyan('gb completion zsh --install')}
|
|
554
|
+
${chalk_1.default.cyan('gb completion fish --install')}
|
|
555
|
+
`)
|
|
556
|
+
.action((shell, options) => {
|
|
557
|
+
const shellLower = shell.toLowerCase();
|
|
558
|
+
// Validate shell
|
|
559
|
+
if (!['bash', 'zsh', 'fish'].includes(shellLower)) {
|
|
560
|
+
console.error(chalk_1.default.red(`Unknown shell: ${shell}`));
|
|
561
|
+
console.error(chalk_1.default.dim('Supported shells: bash, zsh, fish'));
|
|
562
|
+
process.exit(1);
|
|
563
|
+
}
|
|
564
|
+
// If --install flag, install completions
|
|
565
|
+
if (options.install) {
|
|
566
|
+
const config = getShellConfig(shellLower);
|
|
567
|
+
if (!config) {
|
|
568
|
+
console.error(chalk_1.default.red(`Cannot determine config file for ${shell}`));
|
|
569
|
+
process.exit(1);
|
|
570
|
+
}
|
|
571
|
+
// Check if already installed
|
|
572
|
+
if (isCompletionInstalled(shellLower, config)) {
|
|
573
|
+
console.log(chalk_1.default.yellow(`Completions already installed for ${shell}`));
|
|
574
|
+
console.log(chalk_1.default.dim(` Config: ${config.configFile}`));
|
|
575
|
+
return;
|
|
576
|
+
}
|
|
577
|
+
// Install
|
|
578
|
+
const result = installCompletion(shellLower, config);
|
|
579
|
+
if (result.success) {
|
|
580
|
+
console.log(chalk_1.default.green(`✓ ${result.message}`));
|
|
581
|
+
console.log('');
|
|
582
|
+
if (shellLower === 'fish') {
|
|
583
|
+
console.log(chalk_1.default.dim('Completions will be available in new Fish sessions.'));
|
|
584
|
+
}
|
|
585
|
+
else {
|
|
586
|
+
console.log(chalk_1.default.dim('To activate now, run:'));
|
|
587
|
+
console.log(chalk_1.default.cyan(` ${config.reloadCommand}`));
|
|
588
|
+
}
|
|
589
|
+
console.log('');
|
|
590
|
+
console.log(chalk_1.default.dim('Or restart your terminal.'));
|
|
591
|
+
}
|
|
592
|
+
else {
|
|
593
|
+
console.error(chalk_1.default.red(`Failed to install: ${result.message}`));
|
|
594
|
+
process.exit(1);
|
|
595
|
+
}
|
|
596
|
+
return;
|
|
597
|
+
}
|
|
598
|
+
// Otherwise, just output the completion script
|
|
599
|
+
switch (shellLower) {
|
|
600
|
+
case 'bash':
|
|
601
|
+
console.log(generateBashCompletion());
|
|
602
|
+
break;
|
|
603
|
+
case 'zsh':
|
|
604
|
+
console.log(generateZshCompletion());
|
|
605
|
+
break;
|
|
606
|
+
case 'fish':
|
|
607
|
+
console.log(generateFishCompletion());
|
|
608
|
+
break;
|
|
609
|
+
}
|
|
610
|
+
});
|
|
611
|
+
// Detect current shell name
|
|
612
|
+
function detectShell() {
|
|
613
|
+
const shell = process.env.SHELL || '';
|
|
614
|
+
if (shell.includes('bash'))
|
|
615
|
+
return 'bash';
|
|
616
|
+
if (shell.includes('fish'))
|
|
617
|
+
return 'fish';
|
|
618
|
+
if (shell.includes('zsh'))
|
|
619
|
+
return 'zsh';
|
|
620
|
+
return 'zsh'; // Default to zsh
|
|
621
|
+
}
|
|
622
|
+
// Export helper for login command to check if completions are installed
|
|
623
|
+
function isCompletionInstalledForCurrentShell() {
|
|
624
|
+
const shellName = detectShell();
|
|
625
|
+
const config = getShellConfig(shellName);
|
|
626
|
+
if (!config)
|
|
627
|
+
return false;
|
|
628
|
+
return isCompletionInstalled(shellName, config);
|
|
629
|
+
}
|
|
630
|
+
// Export helper for login command to show completion hint
|
|
631
|
+
function getCompletionHint() {
|
|
632
|
+
const shellName = detectShell();
|
|
633
|
+
return `${chalk_1.default.dim('Enable tab completion for a better experience:')}
|
|
634
|
+
${chalk_1.default.cyan(`gb completion ${shellName} --install`)}`;
|
|
635
|
+
}
|
package/dist/commands/list.js
CHANGED
|
@@ -71,11 +71,20 @@ exports.listCommand = new commander_1.Command('list')
|
|
|
71
71
|
// Show project info when listing all
|
|
72
72
|
const projectSuffix = options.all && genbox.project ? ` [${genbox.project}]` : '';
|
|
73
73
|
const nameWithProject = genbox.name + projectSuffix;
|
|
74
|
+
// Determine auto-destroy status first (needed for hour end coloring)
|
|
75
|
+
const now = new Date();
|
|
76
|
+
const minutesInactive = genbox.lastActivityAt
|
|
77
|
+
? Math.floor((now.getTime() - new Date(genbox.lastActivityAt).getTime()) / (60 * 1000))
|
|
78
|
+
: 999; // Assume inactive if no activity data
|
|
79
|
+
// Check if auto-destroy will actually happen
|
|
80
|
+
const isProtectedPermanently = genbox.autoDestroyOnInactivity === false;
|
|
81
|
+
const isProtectedTemporarily = genbox.protectedUntil && new Date(genbox.protectedUntil).getTime() > now.getTime();
|
|
82
|
+
const isAutoDestroyPaused = minutesInactive < 5;
|
|
83
|
+
const willAutoDestroy = !isProtectedPermanently && !isProtectedTemporarily && !isAutoDestroyPaused;
|
|
74
84
|
// Format end hour as relative time (destroy happens at 58 min mark, not 60)
|
|
75
85
|
let endHourInfo = '';
|
|
76
86
|
if (genbox.currentHourEnd && genbox.status === 'running') {
|
|
77
87
|
const endTime = new Date(genbox.currentHourEnd);
|
|
78
|
-
const now = new Date();
|
|
79
88
|
// Subtract 2 minutes since auto-destroy happens at 58 min mark
|
|
80
89
|
const destroyTime = endTime.getTime() - (2 * 60 * 1000);
|
|
81
90
|
const diffMs = destroyTime - now.getTime();
|
|
@@ -86,17 +95,20 @@ exports.listCommand = new commander_1.Command('list')
|
|
|
86
95
|
const timeStr = mins > 0
|
|
87
96
|
? `${mins}m:${secs.toString().padStart(2, '0')}s`
|
|
88
97
|
: `${secs}s`;
|
|
89
|
-
// Red color if less than 5 minutes
|
|
90
|
-
if (mins < 5) {
|
|
98
|
+
// Red color only if less than 5 minutes AND auto-destroy will actually happen
|
|
99
|
+
if (mins < 5 && willAutoDestroy) {
|
|
91
100
|
endHourInfo = chalk_1.default.red(` hour ends in ${timeStr}`);
|
|
92
101
|
}
|
|
93
102
|
else {
|
|
94
103
|
endHourInfo = chalk_1.default.dim(` hour ends in ${timeStr}`);
|
|
95
104
|
}
|
|
96
105
|
}
|
|
97
|
-
else {
|
|
106
|
+
else if (willAutoDestroy) {
|
|
98
107
|
endHourInfo = chalk_1.default.red(' hour ending...');
|
|
99
108
|
}
|
|
109
|
+
else {
|
|
110
|
+
endHourInfo = chalk_1.default.dim(' hour ending...');
|
|
111
|
+
}
|
|
100
112
|
}
|
|
101
113
|
// Show auto-destroy status (not applicable for stopped/terminated)
|
|
102
114
|
let protectedInfo = '';
|
|
@@ -142,7 +154,6 @@ exports.listCommand = new commander_1.Command('list')
|
|
|
142
154
|
}
|
|
143
155
|
else if (genbox.protectedUntil) {
|
|
144
156
|
const protectedUntil = new Date(genbox.protectedUntil);
|
|
145
|
-
const now = new Date();
|
|
146
157
|
const diffMs = protectedUntil.getTime() - now.getTime();
|
|
147
158
|
const hoursRemaining = Math.ceil(diffMs / (1000 * 60 * 60));
|
|
148
159
|
if (hoursRemaining > 0) {
|
|
@@ -154,10 +165,6 @@ exports.listCommand = new commander_1.Command('list')
|
|
|
154
165
|
}
|
|
155
166
|
else {
|
|
156
167
|
// Check if auto-destroy is paused due to recent activity
|
|
157
|
-
const now = new Date();
|
|
158
|
-
const minutesInactive = genbox.lastActivityAt
|
|
159
|
-
? Math.floor((now.getTime() - new Date(genbox.lastActivityAt).getTime()) / (60 * 1000))
|
|
160
|
-
: 999; // Assume inactive if no activity data
|
|
161
168
|
if (minutesInactive < 5) {
|
|
162
169
|
protectedInfo = chalk_1.default.green(' [auto-destroy paused]');
|
|
163
170
|
}
|
package/dist/commands/login.js
CHANGED
|
@@ -9,6 +9,7 @@ const chalk_1 = __importDefault(require("chalk"));
|
|
|
9
9
|
const inquirer_1 = __importDefault(require("inquirer"));
|
|
10
10
|
const api_1 = require("../api");
|
|
11
11
|
const config_store_1 = require("../config-store");
|
|
12
|
+
const completion_1 = require("./completion");
|
|
12
13
|
exports.loginCommand = new commander_1.Command('login')
|
|
13
14
|
.description('Login to Genbox')
|
|
14
15
|
.action(async () => {
|
|
@@ -38,7 +39,12 @@ exports.loginCommand = new commander_1.Command('login')
|
|
|
38
39
|
user: response.user,
|
|
39
40
|
},
|
|
40
41
|
});
|
|
41
|
-
console.log(chalk_1.default.green('Successfully logged in!'));
|
|
42
|
+
console.log(chalk_1.default.green('✓ Successfully logged in!'));
|
|
43
|
+
// Show completion hint if not already installed
|
|
44
|
+
if (!(0, completion_1.isCompletionInstalledForCurrentShell)()) {
|
|
45
|
+
console.log('');
|
|
46
|
+
console.log((0, completion_1.getCompletionHint)());
|
|
47
|
+
}
|
|
42
48
|
}
|
|
43
49
|
else {
|
|
44
50
|
console.error(chalk_1.default.red('Login failed: No token received.'));
|
package/dist/index.js
CHANGED
|
@@ -1,15 +1,12 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
2
|
"use strict";
|
|
3
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
4
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
5
|
+
};
|
|
3
6
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
4
7
|
const commander_1 = require("commander");
|
|
8
|
+
const chalk_1 = __importDefault(require("chalk"));
|
|
5
9
|
const init_1 = require("./commands/init");
|
|
6
|
-
const program = new commander_1.Command();
|
|
7
|
-
// eslint-disable-next-line @typescript-eslint/no-var-requires
|
|
8
|
-
const { version } = require('../package.json');
|
|
9
|
-
program
|
|
10
|
-
.name('genbox')
|
|
11
|
-
.description('Genbox CLI - AI-Powered Development Environments\n\nTIP: Use "gb" as a shorthand (e.g., gb list, gb create)')
|
|
12
|
-
.version(version, '-v, --version', 'Output the current version');
|
|
13
10
|
const create_1 = require("./commands/create");
|
|
14
11
|
const list_1 = require("./commands/list");
|
|
15
12
|
const destroy_1 = require("./commands/destroy");
|
|
@@ -39,6 +36,127 @@ const stop_1 = require("./commands/stop");
|
|
|
39
36
|
const start_1 = require("./commands/start");
|
|
40
37
|
const template_1 = require("./commands/template");
|
|
41
38
|
const run_prompt_1 = require("./commands/run-prompt");
|
|
39
|
+
const completion_1 = require("./commands/completion");
|
|
40
|
+
// eslint-disable-next-line @typescript-eslint/no-var-requires
|
|
41
|
+
const { version } = require('../package.json');
|
|
42
|
+
const commandCategories = {
|
|
43
|
+
'CORE COMMANDS': [
|
|
44
|
+
{ name: 'create', aliases: [], description: 'Create a new Genbox environment' },
|
|
45
|
+
{ name: 'list', aliases: ['ls'], description: 'List genboxes' },
|
|
46
|
+
{ name: 'destroy', aliases: ['delete'], description: 'Destroy a Genbox' },
|
|
47
|
+
{ name: 'connect', aliases: [], description: 'SSH into a Genbox' },
|
|
48
|
+
{ name: 'status', aliases: [], description: 'Check Genbox status and services' },
|
|
49
|
+
],
|
|
50
|
+
'LIFECYCLE': [
|
|
51
|
+
{ name: 'start', aliases: ['resume'], description: 'Start a stopped Genbox' },
|
|
52
|
+
{ name: 'stop', aliases: [], description: 'Stop a running Genbox' },
|
|
53
|
+
{ name: 'restart', aliases: [], description: 'Restart services in a Genbox' },
|
|
54
|
+
{ name: 'extend', aliases: [], description: 'Extend Genbox lifetime' },
|
|
55
|
+
{ name: 'rebuild', aliases: [], description: 'Rebuild a Genbox with new config' },
|
|
56
|
+
],
|
|
57
|
+
'DEVELOPMENT': [
|
|
58
|
+
{ name: 'urls', aliases: [], description: 'Show service URLs' },
|
|
59
|
+
{ name: 'forward', aliases: [], description: 'Set up port forwarding' },
|
|
60
|
+
{ name: 'push', aliases: [], description: 'Push local changes' },
|
|
61
|
+
{ name: 'run-prompt', aliases: ['run'], description: 'Run Claude Code prompt remotely' },
|
|
62
|
+
],
|
|
63
|
+
'DATABASE': [
|
|
64
|
+
{ name: 'db', aliases: [], description: 'Database operations (sync, restore, snapshots)' },
|
|
65
|
+
{ name: 'restore-db', aliases: [], description: 'Restore local MongoDB to Genbox' },
|
|
66
|
+
],
|
|
67
|
+
'BACKUP & RESTORE': [
|
|
68
|
+
{ name: 'backup', aliases: [], description: 'Create a backup' },
|
|
69
|
+
{ name: 'backups', aliases: [], description: 'List and manage backups' },
|
|
70
|
+
{ name: 'template', aliases: [], description: 'Manage project templates' },
|
|
71
|
+
],
|
|
72
|
+
'CONFIGURATION': [
|
|
73
|
+
{ name: 'init', aliases: [], description: 'Initialize genbox.yaml' },
|
|
74
|
+
{ name: 'config', aliases: [], description: 'Inspect configuration' },
|
|
75
|
+
{ name: 'profiles', aliases: [], description: 'Manage profiles' },
|
|
76
|
+
{ name: 'resolve', aliases: [], description: 'Compute final configuration' },
|
|
77
|
+
{ name: 'validate', aliases: [], description: 'Validate configuration files' },
|
|
78
|
+
],
|
|
79
|
+
'ACCOUNT': [
|
|
80
|
+
{ name: 'login', aliases: [], description: 'Authenticate with Genbox' },
|
|
81
|
+
{ name: 'balance', aliases: [], description: 'Show credit balance' },
|
|
82
|
+
],
|
|
83
|
+
'HELP': [
|
|
84
|
+
{ name: 'help', aliases: [], description: 'Show detailed help and examples' },
|
|
85
|
+
{ name: 'completion', aliases: [], description: 'Generate shell completions' },
|
|
86
|
+
],
|
|
87
|
+
};
|
|
88
|
+
function showCustomHelp() {
|
|
89
|
+
const output = [];
|
|
90
|
+
// Header
|
|
91
|
+
output.push('Genbox CLI - AI-Powered Development Environments');
|
|
92
|
+
output.push('');
|
|
93
|
+
output.push(chalk_1.default.green('TIP:') + ' Use ' + chalk_1.default.cyan('"gb"') + ' as a shorthand (e.g., gb list, gb create)');
|
|
94
|
+
output.push('');
|
|
95
|
+
// Usage
|
|
96
|
+
output.push(chalk_1.default.bold('USAGE'));
|
|
97
|
+
output.push(' genbox <command> [options]');
|
|
98
|
+
output.push('');
|
|
99
|
+
// Categorized commands
|
|
100
|
+
for (const [category, commands] of Object.entries(commandCategories)) {
|
|
101
|
+
output.push(chalk_1.default.bold(category));
|
|
102
|
+
for (const cmd of commands) {
|
|
103
|
+
const aliasStr = cmd.aliases.length > 0 ? chalk_1.default.dim(` (${cmd.aliases.join(', ')})`) : '';
|
|
104
|
+
const padding = Math.max(2, 22 - cmd.name.length - (cmd.aliases.length > 0 ? cmd.aliases[0].length + 4 : 0));
|
|
105
|
+
output.push(` ${chalk_1.default.cyan(cmd.name)}${aliasStr}${' '.repeat(padding)}${cmd.description}`);
|
|
106
|
+
}
|
|
107
|
+
output.push('');
|
|
108
|
+
}
|
|
109
|
+
// Global options
|
|
110
|
+
output.push(chalk_1.default.bold('OPTIONS'));
|
|
111
|
+
output.push(` ${chalk_1.default.cyan('-v, --version')} Show version number`);
|
|
112
|
+
output.push(` ${chalk_1.default.cyan('-h, --help')} Show help for command`);
|
|
113
|
+
output.push('');
|
|
114
|
+
// Examples
|
|
115
|
+
output.push(chalk_1.default.bold('EXAMPLES'));
|
|
116
|
+
output.push(chalk_1.default.dim(' # Create a new development environment'));
|
|
117
|
+
output.push(` ${chalk_1.default.cyan('$ gb create feature-auth')}`);
|
|
118
|
+
output.push('');
|
|
119
|
+
output.push(chalk_1.default.dim(' # Check status and wait for setup'));
|
|
120
|
+
output.push(` ${chalk_1.default.cyan('$ gb status -w')}`);
|
|
121
|
+
output.push('');
|
|
122
|
+
output.push(chalk_1.default.dim(' # Connect via SSH'));
|
|
123
|
+
output.push(` ${chalk_1.default.cyan('$ gb connect')}`);
|
|
124
|
+
output.push('');
|
|
125
|
+
output.push(chalk_1.default.dim(' # List all your genboxes'));
|
|
126
|
+
output.push(` ${chalk_1.default.cyan('$ gb list')}`);
|
|
127
|
+
output.push('');
|
|
128
|
+
// More help
|
|
129
|
+
output.push(chalk_1.default.bold('LEARN MORE'));
|
|
130
|
+
output.push(` Run ${chalk_1.default.cyan('gb help')} for detailed guides and workflow examples`);
|
|
131
|
+
output.push(` Run ${chalk_1.default.cyan('gb <command> --help')} for command-specific help`);
|
|
132
|
+
output.push(` Documentation: ${chalk_1.default.cyan('https://genbox.dev/docs')}`);
|
|
133
|
+
output.push('');
|
|
134
|
+
console.log(output.join('\n'));
|
|
135
|
+
}
|
|
136
|
+
const program = new commander_1.Command();
|
|
137
|
+
program
|
|
138
|
+
.name('genbox')
|
|
139
|
+
.description('Genbox CLI - AI-Powered Development Environments')
|
|
140
|
+
.version(version, '-v, --version', 'Show version number')
|
|
141
|
+
.helpOption('-h, --help', 'Show help for command')
|
|
142
|
+
.addHelpCommand(false); // Disable default help subcommand
|
|
143
|
+
// Custom help handler for root command
|
|
144
|
+
program.on('option:help', () => {
|
|
145
|
+
showCustomHelp();
|
|
146
|
+
process.exit(0);
|
|
147
|
+
});
|
|
148
|
+
// Handle --help as first arg (before parsing)
|
|
149
|
+
if (process.argv.includes('--help') || process.argv.includes('-h')) {
|
|
150
|
+
// Check if it's for root command (no subcommand before --help)
|
|
151
|
+
const args = process.argv.slice(2);
|
|
152
|
+
const helpIndex = args.findIndex(a => a === '--help' || a === '-h');
|
|
153
|
+
const hasSubcommandBeforeHelp = helpIndex > 0 && !args[0].startsWith('-');
|
|
154
|
+
if (!hasSubcommandBeforeHelp) {
|
|
155
|
+
showCustomHelp();
|
|
156
|
+
process.exit(0);
|
|
157
|
+
}
|
|
158
|
+
}
|
|
159
|
+
// Add all commands
|
|
42
160
|
program
|
|
43
161
|
.addCommand(init_1.initCommand)
|
|
44
162
|
.addCommand(create_1.createCommand)
|
|
@@ -58,17 +176,18 @@ program
|
|
|
58
176
|
.addCommand(config_1.configCommand)
|
|
59
177
|
.addCommand(resolve_1.resolveCommand)
|
|
60
178
|
.addCommand(validate_1.validateCommand)
|
|
61
|
-
.addCommand(migrate_1.migrateCommand)
|
|
62
|
-
.addCommand(migrate_1.deprecationsCommand)
|
|
63
|
-
.addCommand(ssh_setup_1.sshSetupCommand)
|
|
179
|
+
.addCommand(migrate_1.migrateCommand, { hidden: true })
|
|
180
|
+
.addCommand(migrate_1.deprecationsCommand, { hidden: true })
|
|
181
|
+
.addCommand(ssh_setup_1.sshSetupCommand, { hidden: true })
|
|
64
182
|
.addCommand(rebuild_1.rebuildCommand)
|
|
65
183
|
.addCommand(extend_1.extendCommand)
|
|
66
|
-
.addCommand(cleanup_ssh_1.cleanupSshCommand)
|
|
184
|
+
.addCommand(cleanup_ssh_1.cleanupSshCommand, { hidden: true })
|
|
67
185
|
.addCommand(restart_1.restartCommand)
|
|
68
186
|
.addCommand(backup_1.backupCommand)
|
|
69
187
|
.addCommand(backups_1.backupsCommand)
|
|
70
188
|
.addCommand(stop_1.stopCommand)
|
|
71
189
|
.addCommand(start_1.startCommand)
|
|
72
190
|
.addCommand(template_1.templateCommand)
|
|
73
|
-
.addCommand(run_prompt_1.runPromptCommand)
|
|
191
|
+
.addCommand(run_prompt_1.runPromptCommand)
|
|
192
|
+
.addCommand(completion_1.completionCommand);
|
|
74
193
|
program.parse(process.argv);
|