@a5c-ai/agent-mux-cli 0.2.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/LICENSE +21 -0
- package/README.md +28 -0
- package/dist/bootstrap.d.ts +14 -0
- package/dist/bootstrap.d.ts.map +1 -0
- package/dist/bootstrap.js +41 -0
- package/dist/bootstrap.js.map +1 -0
- package/dist/commands/adapters.d.ts +9 -0
- package/dist/commands/adapters.d.ts.map +1 -0
- package/dist/commands/adapters.js +132 -0
- package/dist/commands/adapters.js.map +1 -0
- package/dist/commands/auth.d.ts +9 -0
- package/dist/commands/auth.d.ts.map +1 -0
- package/dist/commands/auth.js +137 -0
- package/dist/commands/auth.js.map +1 -0
- package/dist/commands/config.d.ts +9 -0
- package/dist/commands/config.d.ts.map +1 -0
- package/dist/commands/config.js +221 -0
- package/dist/commands/config.js.map +1 -0
- package/dist/commands/detect-host.d.ts +8 -0
- package/dist/commands/detect-host.d.ts.map +1 -0
- package/dist/commands/detect-host.js +33 -0
- package/dist/commands/detect-host.js.map +1 -0
- package/dist/commands/doctor.d.ts +4 -0
- package/dist/commands/doctor.d.ts.map +1 -0
- package/dist/commands/doctor.js +120 -0
- package/dist/commands/doctor.js.map +1 -0
- package/dist/commands/help.d.ts +14 -0
- package/dist/commands/help.d.ts.map +1 -0
- package/dist/commands/help.js +346 -0
- package/dist/commands/help.js.map +1 -0
- package/dist/commands/hooks.d.ts +17 -0
- package/dist/commands/hooks.d.ts.map +1 -0
- package/dist/commands/hooks.js +219 -0
- package/dist/commands/hooks.js.map +1 -0
- package/dist/commands/install-helpers.d.ts +25 -0
- package/dist/commands/install-helpers.d.ts.map +1 -0
- package/dist/commands/install-helpers.js +58 -0
- package/dist/commands/install-helpers.js.map +1 -0
- package/dist/commands/install.d.ts +25 -0
- package/dist/commands/install.d.ts.map +1 -0
- package/dist/commands/install.js +406 -0
- package/dist/commands/install.js.map +1 -0
- package/dist/commands/models.d.ts +9 -0
- package/dist/commands/models.d.ts.map +1 -0
- package/dist/commands/models.js +153 -0
- package/dist/commands/models.js.map +1 -0
- package/dist/commands/plugins.d.ts +9 -0
- package/dist/commands/plugins.d.ts.map +1 -0
- package/dist/commands/plugins.js +180 -0
- package/dist/commands/plugins.js.map +1 -0
- package/dist/commands/profiles.d.ts +9 -0
- package/dist/commands/profiles.d.ts.map +1 -0
- package/dist/commands/profiles.js +206 -0
- package/dist/commands/profiles.js.map +1 -0
- package/dist/commands/remote.d.ts +31 -0
- package/dist/commands/remote.d.ts.map +1 -0
- package/dist/commands/remote.js +204 -0
- package/dist/commands/remote.js.map +1 -0
- package/dist/commands/run.d.ts +28 -0
- package/dist/commands/run.d.ts.map +1 -0
- package/dist/commands/run.js +293 -0
- package/dist/commands/run.js.map +1 -0
- package/dist/commands/sessions.d.ts +9 -0
- package/dist/commands/sessions.d.ts.map +1 -0
- package/dist/commands/sessions.js +225 -0
- package/dist/commands/sessions.js.map +1 -0
- package/dist/exit-codes.d.ts +33 -0
- package/dist/exit-codes.d.ts.map +1 -0
- package/dist/exit-codes.js +68 -0
- package/dist/exit-codes.js.map +1 -0
- package/dist/index.d.ts +23 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +188 -0
- package/dist/index.js.map +1 -0
- package/dist/output.d.ts +56 -0
- package/dist/output.d.ts.map +1 -0
- package/dist/output.js +129 -0
- package/dist/output.js.map +1 -0
- package/dist/parse-args.d.ts +58 -0
- package/dist/parse-args.d.ts.map +1 -0
- package/dist/parse-args.js +257 -0
- package/dist/parse-args.js.map +1 -0
- package/package.json +57 -0
|
@@ -0,0 +1,180 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* `amux plugins` subcommands.
|
|
3
|
+
*
|
|
4
|
+
* @see docs/10-cli-reference.md Section 11
|
|
5
|
+
*/
|
|
6
|
+
import { AgentMuxError } from '@a5c-ai/agent-mux-core';
|
|
7
|
+
import { flagBool, flagStr } from '../parse-args.js';
|
|
8
|
+
import { ExitCode, errorCodeToExitCode } from '../exit-codes.js';
|
|
9
|
+
import { printTable, printJsonOk, printJsonError, printError, } from '../output.js';
|
|
10
|
+
export async function pluginsCommand(client, args) {
|
|
11
|
+
const sub = args.subcommand;
|
|
12
|
+
const jsonMode = flagBool(args.flags, 'json') === true;
|
|
13
|
+
if (sub === 'list') {
|
|
14
|
+
const agent = args.positionals[0] ?? flagStr(args.flags, 'agent');
|
|
15
|
+
if (!agent) {
|
|
16
|
+
if (jsonMode) {
|
|
17
|
+
printJsonError('VALIDATION_ERROR', 'Missing required argument: <agent>');
|
|
18
|
+
}
|
|
19
|
+
else {
|
|
20
|
+
printError('Missing required argument: <agent>');
|
|
21
|
+
}
|
|
22
|
+
return ExitCode.USAGE_ERROR;
|
|
23
|
+
}
|
|
24
|
+
return pluginsList(client, agent, jsonMode);
|
|
25
|
+
}
|
|
26
|
+
if (sub === 'install') {
|
|
27
|
+
const agent = args.positionals[0];
|
|
28
|
+
const plugin = args.positionals[1];
|
|
29
|
+
if (!agent || !plugin) {
|
|
30
|
+
if (jsonMode) {
|
|
31
|
+
printJsonError('VALIDATION_ERROR', 'Usage: amux plugins install <agent> <plugin>');
|
|
32
|
+
}
|
|
33
|
+
else {
|
|
34
|
+
printError('Usage: amux plugins install <agent> <plugin>');
|
|
35
|
+
}
|
|
36
|
+
return ExitCode.USAGE_ERROR;
|
|
37
|
+
}
|
|
38
|
+
return pluginsInstall(client, agent, plugin, args, jsonMode);
|
|
39
|
+
}
|
|
40
|
+
if (sub === 'uninstall') {
|
|
41
|
+
const agent = args.positionals[0];
|
|
42
|
+
const plugin = args.positionals[1];
|
|
43
|
+
if (!agent || !plugin) {
|
|
44
|
+
if (jsonMode) {
|
|
45
|
+
printJsonError('VALIDATION_ERROR', 'Usage: amux plugins uninstall <agent> <plugin>');
|
|
46
|
+
}
|
|
47
|
+
else {
|
|
48
|
+
printError('Usage: amux plugins uninstall <agent> <plugin>');
|
|
49
|
+
}
|
|
50
|
+
return ExitCode.USAGE_ERROR;
|
|
51
|
+
}
|
|
52
|
+
return pluginsUninstall(client, agent, plugin, jsonMode);
|
|
53
|
+
}
|
|
54
|
+
if (!sub) {
|
|
55
|
+
if (jsonMode) {
|
|
56
|
+
printJsonError('VALIDATION_ERROR', 'Missing subcommand. Available: list, install, uninstall');
|
|
57
|
+
}
|
|
58
|
+
else {
|
|
59
|
+
printError('Missing subcommand. Available: list, install, uninstall');
|
|
60
|
+
}
|
|
61
|
+
return ExitCode.USAGE_ERROR;
|
|
62
|
+
}
|
|
63
|
+
if (jsonMode) {
|
|
64
|
+
printJsonError('VALIDATION_ERROR', `Unknown subcommand: plugins ${sub}`);
|
|
65
|
+
}
|
|
66
|
+
else {
|
|
67
|
+
printError(`Unknown subcommand: plugins ${sub}`);
|
|
68
|
+
}
|
|
69
|
+
return ExitCode.USAGE_ERROR;
|
|
70
|
+
}
|
|
71
|
+
async function pluginsList(client, agent, jsonMode) {
|
|
72
|
+
try {
|
|
73
|
+
// PluginManager is currently a stub — gracefully handle
|
|
74
|
+
// PluginManager is a stub interface at this phase; accessing optional
|
|
75
|
+
// methods/properties by string key requires a loose view.
|
|
76
|
+
const pm = client.plugins;
|
|
77
|
+
if (pm['_stub']) {
|
|
78
|
+
if (jsonMode) {
|
|
79
|
+
printJsonOk([]);
|
|
80
|
+
}
|
|
81
|
+
else {
|
|
82
|
+
process.stdout.write('Plugin management is not yet implemented.\n');
|
|
83
|
+
}
|
|
84
|
+
return ExitCode.SUCCESS;
|
|
85
|
+
}
|
|
86
|
+
const list = (await pm['list']?.(agent)) ?? [];
|
|
87
|
+
if (jsonMode) {
|
|
88
|
+
printJsonOk(list);
|
|
89
|
+
return ExitCode.SUCCESS;
|
|
90
|
+
}
|
|
91
|
+
const rows = list.map((p) => [
|
|
92
|
+
String(p['id'] ?? '--'),
|
|
93
|
+
String(p['name'] ?? '--'),
|
|
94
|
+
String(p['version'] ?? '--'),
|
|
95
|
+
String(p['format'] ?? '--'),
|
|
96
|
+
p['enabled'] ? 'yes' : 'no',
|
|
97
|
+
]);
|
|
98
|
+
printTable(['Plugin ID', 'Name', 'Version', 'Format', 'Enabled'], rows);
|
|
99
|
+
return ExitCode.SUCCESS;
|
|
100
|
+
}
|
|
101
|
+
catch (err) {
|
|
102
|
+
return handleError(err, jsonMode);
|
|
103
|
+
}
|
|
104
|
+
}
|
|
105
|
+
async function pluginsInstall(client, agent, plugin, args, jsonMode) {
|
|
106
|
+
try {
|
|
107
|
+
// PluginManager is a stub interface at this phase; accessing optional
|
|
108
|
+
// methods/properties by string key requires a loose view.
|
|
109
|
+
const pm = client.plugins;
|
|
110
|
+
if (pm['_stub']) {
|
|
111
|
+
if (jsonMode) {
|
|
112
|
+
printJsonError('PLUGIN_ERROR', 'Plugin management is not yet implemented');
|
|
113
|
+
}
|
|
114
|
+
else {
|
|
115
|
+
printError('Plugin management is not yet implemented.');
|
|
116
|
+
}
|
|
117
|
+
return ExitCode.PLUGIN_ERROR;
|
|
118
|
+
}
|
|
119
|
+
const version = flagStr(args.flags, 'version');
|
|
120
|
+
const global = flagBool(args.flags, 'global');
|
|
121
|
+
await pm['install']?.(agent, plugin, { version, global });
|
|
122
|
+
if (jsonMode) {
|
|
123
|
+
printJsonOk({ installed: plugin, agent });
|
|
124
|
+
}
|
|
125
|
+
else {
|
|
126
|
+
process.stdout.write(`Plugin "${plugin}" installed for ${agent}.\n`);
|
|
127
|
+
}
|
|
128
|
+
return ExitCode.SUCCESS;
|
|
129
|
+
}
|
|
130
|
+
catch (err) {
|
|
131
|
+
return handleError(err, jsonMode);
|
|
132
|
+
}
|
|
133
|
+
}
|
|
134
|
+
async function pluginsUninstall(client, agent, plugin, jsonMode) {
|
|
135
|
+
try {
|
|
136
|
+
// PluginManager is a stub interface at this phase; accessing optional
|
|
137
|
+
// methods/properties by string key requires a loose view.
|
|
138
|
+
const pm = client.plugins;
|
|
139
|
+
if (pm['_stub']) {
|
|
140
|
+
if (jsonMode) {
|
|
141
|
+
printJsonError('PLUGIN_ERROR', 'Plugin management is not yet implemented');
|
|
142
|
+
}
|
|
143
|
+
else {
|
|
144
|
+
printError('Plugin management is not yet implemented.');
|
|
145
|
+
}
|
|
146
|
+
return ExitCode.PLUGIN_ERROR;
|
|
147
|
+
}
|
|
148
|
+
await pm['uninstall']?.(agent, plugin);
|
|
149
|
+
if (jsonMode) {
|
|
150
|
+
printJsonOk({ uninstalled: plugin, agent });
|
|
151
|
+
}
|
|
152
|
+
else {
|
|
153
|
+
process.stdout.write(`Plugin "${plugin}" uninstalled from ${agent}.\n`);
|
|
154
|
+
}
|
|
155
|
+
return ExitCode.SUCCESS;
|
|
156
|
+
}
|
|
157
|
+
catch (err) {
|
|
158
|
+
return handleError(err, jsonMode);
|
|
159
|
+
}
|
|
160
|
+
}
|
|
161
|
+
function handleError(err, jsonMode) {
|
|
162
|
+
if (err instanceof AgentMuxError) {
|
|
163
|
+
if (jsonMode) {
|
|
164
|
+
printJsonError(err.code, err.message, err.recoverable);
|
|
165
|
+
}
|
|
166
|
+
else {
|
|
167
|
+
printError(err.message);
|
|
168
|
+
}
|
|
169
|
+
return errorCodeToExitCode(err.code);
|
|
170
|
+
}
|
|
171
|
+
const message = err instanceof Error ? err.message : String(err);
|
|
172
|
+
if (jsonMode) {
|
|
173
|
+
printJsonError('INTERNAL', message);
|
|
174
|
+
}
|
|
175
|
+
else {
|
|
176
|
+
printError(message);
|
|
177
|
+
}
|
|
178
|
+
return ExitCode.GENERAL_ERROR;
|
|
179
|
+
}
|
|
180
|
+
//# sourceMappingURL=plugins.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"plugins.js","sourceRoot":"","sources":["../../src/commands/plugins.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* `amux profiles` subcommands.
|
|
3
|
+
*
|
|
4
|
+
* @see docs/10-cli-reference.md Section 17
|
|
5
|
+
*/
|
|
6
|
+
import type { AgentMuxClient } from '@a5c-ai/agent-mux-core';
|
|
7
|
+
import type { ParsedArgs } from '../parse-args.js';
|
|
8
|
+
export declare function profilesCommand(client: AgentMuxClient, args: ParsedArgs): Promise<number>;
|
|
9
|
+
//# sourceMappingURL=profiles.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"profiles.d.ts","sourceRoot":"","sources":["../../src/commands/profiles.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,wBAAwB,CAAC;AAE7D,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,kBAAkB,CAAC;AAOnD,wBAAsB,eAAe,CAAC,MAAM,EAAE,cAAc,EAAE,IAAI,EAAE,UAAU,GAAG,OAAO,CAAC,MAAM,CAAC,CAkE/F"}
|
|
@@ -0,0 +1,206 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* `amux profiles` subcommands.
|
|
3
|
+
*
|
|
4
|
+
* @see docs/10-cli-reference.md Section 17
|
|
5
|
+
*/
|
|
6
|
+
import { AgentMuxError } from '@a5c-ai/agent-mux-core';
|
|
7
|
+
import { flagBool, flagStr } from '../parse-args.js';
|
|
8
|
+
import { ExitCode, errorCodeToExitCode } from '../exit-codes.js';
|
|
9
|
+
import { printTable, printJsonOk, printJsonError, printError, printJson, toPlain, } from '../output.js';
|
|
10
|
+
export async function profilesCommand(client, args) {
|
|
11
|
+
const sub = args.subcommand;
|
|
12
|
+
const jsonMode = flagBool(args.flags, 'json') === true;
|
|
13
|
+
if (sub === 'list' || !sub) {
|
|
14
|
+
return profilesList(client, args, jsonMode);
|
|
15
|
+
}
|
|
16
|
+
if (sub === 'show') {
|
|
17
|
+
const name = args.positionals[0];
|
|
18
|
+
if (!name) {
|
|
19
|
+
if (jsonMode) {
|
|
20
|
+
printJsonError('VALIDATION_ERROR', 'Missing required argument: <name>');
|
|
21
|
+
}
|
|
22
|
+
else {
|
|
23
|
+
printError('Missing required argument: <name>');
|
|
24
|
+
}
|
|
25
|
+
return ExitCode.USAGE_ERROR;
|
|
26
|
+
}
|
|
27
|
+
return profilesShow(client, name, jsonMode);
|
|
28
|
+
}
|
|
29
|
+
if (sub === 'set') {
|
|
30
|
+
const name = args.positionals[0];
|
|
31
|
+
if (!name) {
|
|
32
|
+
if (jsonMode) {
|
|
33
|
+
printJsonError('VALIDATION_ERROR', 'Missing required argument: <name>');
|
|
34
|
+
}
|
|
35
|
+
else {
|
|
36
|
+
printError('Missing required argument: <name>');
|
|
37
|
+
}
|
|
38
|
+
return ExitCode.USAGE_ERROR;
|
|
39
|
+
}
|
|
40
|
+
return profilesSet(client, name, args, jsonMode);
|
|
41
|
+
}
|
|
42
|
+
if (sub === 'delete') {
|
|
43
|
+
const name = args.positionals[0];
|
|
44
|
+
if (!name) {
|
|
45
|
+
if (jsonMode) {
|
|
46
|
+
printJsonError('VALIDATION_ERROR', 'Missing required argument: <name>');
|
|
47
|
+
}
|
|
48
|
+
else {
|
|
49
|
+
printError('Missing required argument: <name>');
|
|
50
|
+
}
|
|
51
|
+
return ExitCode.USAGE_ERROR;
|
|
52
|
+
}
|
|
53
|
+
return profilesDelete(client, name, args, jsonMode);
|
|
54
|
+
}
|
|
55
|
+
if (sub === 'apply') {
|
|
56
|
+
const name = args.positionals[0];
|
|
57
|
+
if (!name) {
|
|
58
|
+
if (jsonMode) {
|
|
59
|
+
printJsonError('VALIDATION_ERROR', 'Missing required argument: <name>');
|
|
60
|
+
}
|
|
61
|
+
else {
|
|
62
|
+
printError('Missing required argument: <name>');
|
|
63
|
+
}
|
|
64
|
+
return ExitCode.USAGE_ERROR;
|
|
65
|
+
}
|
|
66
|
+
return profilesApply(client, name, jsonMode);
|
|
67
|
+
}
|
|
68
|
+
if (jsonMode) {
|
|
69
|
+
printJsonError('VALIDATION_ERROR', `Unknown subcommand: profiles ${sub}`);
|
|
70
|
+
}
|
|
71
|
+
else {
|
|
72
|
+
printError(`Unknown subcommand: profiles ${sub}`);
|
|
73
|
+
}
|
|
74
|
+
return ExitCode.USAGE_ERROR;
|
|
75
|
+
}
|
|
76
|
+
function parseScope(raw) {
|
|
77
|
+
if (raw === undefined)
|
|
78
|
+
return undefined;
|
|
79
|
+
if (raw === 'global' || raw === 'project')
|
|
80
|
+
return raw;
|
|
81
|
+
throw new Error(`Invalid --scope: "${raw}" (expected "global" or "project")`);
|
|
82
|
+
}
|
|
83
|
+
async function profilesList(client, args, jsonMode) {
|
|
84
|
+
try {
|
|
85
|
+
const scope = parseScope(flagStr(args.flags, 'scope'));
|
|
86
|
+
const opts = scope ? { scope } : undefined;
|
|
87
|
+
const profiles = await client.profiles.list(opts);
|
|
88
|
+
if (jsonMode) {
|
|
89
|
+
printJsonOk(profiles);
|
|
90
|
+
return ExitCode.SUCCESS;
|
|
91
|
+
}
|
|
92
|
+
const rows = profiles.map((profile) => {
|
|
93
|
+
const p = toPlain(profile);
|
|
94
|
+
return [
|
|
95
|
+
String(p['name'] ?? '--'),
|
|
96
|
+
String(p['scope'] ?? '--'),
|
|
97
|
+
String(p['agent'] ?? '--'),
|
|
98
|
+
String(p['model'] ?? '--'),
|
|
99
|
+
];
|
|
100
|
+
});
|
|
101
|
+
printTable(['Name', 'Scope', 'Agent', 'Model'], rows);
|
|
102
|
+
return ExitCode.SUCCESS;
|
|
103
|
+
}
|
|
104
|
+
catch (err) {
|
|
105
|
+
return handleError(err, jsonMode);
|
|
106
|
+
}
|
|
107
|
+
}
|
|
108
|
+
async function profilesShow(client, name, jsonMode) {
|
|
109
|
+
try {
|
|
110
|
+
const profile = await client.profiles.show(name);
|
|
111
|
+
if (jsonMode) {
|
|
112
|
+
printJsonOk(profile);
|
|
113
|
+
}
|
|
114
|
+
else {
|
|
115
|
+
printJson(profile);
|
|
116
|
+
}
|
|
117
|
+
return ExitCode.SUCCESS;
|
|
118
|
+
}
|
|
119
|
+
catch (err) {
|
|
120
|
+
return handleError(err, jsonMode);
|
|
121
|
+
}
|
|
122
|
+
}
|
|
123
|
+
async function profilesSet(client, name, args, jsonMode) {
|
|
124
|
+
try {
|
|
125
|
+
// Build profile data from remaining flags
|
|
126
|
+
const data = {};
|
|
127
|
+
const scope = parseScope(flagStr(args.flags, 'scope'));
|
|
128
|
+
const agent = flagStr(args.flags, 'agent');
|
|
129
|
+
const model = flagStr(args.flags, 'model');
|
|
130
|
+
if (agent)
|
|
131
|
+
data['agent'] = agent;
|
|
132
|
+
if (model)
|
|
133
|
+
data['model'] = model;
|
|
134
|
+
// Pass through known run flags
|
|
135
|
+
for (const key of Object.keys(args.flags)) {
|
|
136
|
+
if (['agent', 'model', 'scope', 'json', 'help', 'debug', 'config-dir', 'project-dir', 'no-color', 'version'].includes(key)) {
|
|
137
|
+
continue;
|
|
138
|
+
}
|
|
139
|
+
data[key] = args.flags[key];
|
|
140
|
+
}
|
|
141
|
+
const opts = scope ? { scope } : undefined;
|
|
142
|
+
await client.profiles.set(name, data, opts);
|
|
143
|
+
if (jsonMode) {
|
|
144
|
+
printJsonOk({ name, data });
|
|
145
|
+
}
|
|
146
|
+
else {
|
|
147
|
+
process.stdout.write(`Profile "${name}" saved.\n`);
|
|
148
|
+
}
|
|
149
|
+
return ExitCode.SUCCESS;
|
|
150
|
+
}
|
|
151
|
+
catch (err) {
|
|
152
|
+
return handleError(err, jsonMode);
|
|
153
|
+
}
|
|
154
|
+
}
|
|
155
|
+
async function profilesDelete(client, name, args, jsonMode) {
|
|
156
|
+
try {
|
|
157
|
+
const scope = parseScope(flagStr(args.flags, 'scope'));
|
|
158
|
+
const opts = scope ? { scope } : undefined;
|
|
159
|
+
await client.profiles.delete(name, opts);
|
|
160
|
+
if (jsonMode) {
|
|
161
|
+
printJsonOk({ deleted: name });
|
|
162
|
+
}
|
|
163
|
+
else {
|
|
164
|
+
process.stdout.write(`Profile "${name}" deleted.\n`);
|
|
165
|
+
}
|
|
166
|
+
return ExitCode.SUCCESS;
|
|
167
|
+
}
|
|
168
|
+
catch (err) {
|
|
169
|
+
return handleError(err, jsonMode);
|
|
170
|
+
}
|
|
171
|
+
}
|
|
172
|
+
async function profilesApply(client, name, jsonMode) {
|
|
173
|
+
try {
|
|
174
|
+
const resolved = await client.profiles.apply(name);
|
|
175
|
+
if (jsonMode) {
|
|
176
|
+
printJsonOk(resolved);
|
|
177
|
+
}
|
|
178
|
+
else {
|
|
179
|
+
printJson(resolved);
|
|
180
|
+
}
|
|
181
|
+
return ExitCode.SUCCESS;
|
|
182
|
+
}
|
|
183
|
+
catch (err) {
|
|
184
|
+
return handleError(err, jsonMode);
|
|
185
|
+
}
|
|
186
|
+
}
|
|
187
|
+
function handleError(err, jsonMode) {
|
|
188
|
+
if (err instanceof AgentMuxError) {
|
|
189
|
+
if (jsonMode) {
|
|
190
|
+
printJsonError(err.code, err.message, err.recoverable);
|
|
191
|
+
}
|
|
192
|
+
else {
|
|
193
|
+
printError(err.message);
|
|
194
|
+
}
|
|
195
|
+
return errorCodeToExitCode(err.code);
|
|
196
|
+
}
|
|
197
|
+
const message = err instanceof Error ? err.message : String(err);
|
|
198
|
+
if (jsonMode) {
|
|
199
|
+
printJsonError('INTERNAL', message);
|
|
200
|
+
}
|
|
201
|
+
else {
|
|
202
|
+
printError(message);
|
|
203
|
+
}
|
|
204
|
+
return ExitCode.GENERAL_ERROR;
|
|
205
|
+
}
|
|
206
|
+
//# sourceMappingURL=profiles.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"profiles.js","sourceRoot":"","sources":["../../src/commands/profiles.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* `amux remote install <host>` / `amux remote update <host>`.
|
|
3
|
+
*
|
|
4
|
+
* Self-install pipeline — uses `buildInvocationCommand()` to build each step
|
|
5
|
+
* so the transport (ssh/docker/k8s) is selectable via `--mode` and works
|
|
6
|
+
* uniformly across environments.
|
|
7
|
+
*
|
|
8
|
+
* Steps:
|
|
9
|
+
* 1. Probe: `amux --version` — check if amux is on the remote.
|
|
10
|
+
* 2. Install: `npm install -g @a5c-ai/agent-mux-cli` if missing (or --force).
|
|
11
|
+
* 3. Harness: `amux install <harness>` — deploy the desired harness.
|
|
12
|
+
* 4. Verify: `amux detect --all --json` — confirm the harness is active.
|
|
13
|
+
*/
|
|
14
|
+
import type { AgentMuxClient } from '@a5c-ai/agent-mux-core';
|
|
15
|
+
import type { ParsedArgs, FlagDef } from '../parse-args.js';
|
|
16
|
+
export declare const REMOTE_FLAGS: Record<string, FlagDef>;
|
|
17
|
+
/** Minimal spawner used by the remote command. Injectable for tests. */
|
|
18
|
+
export type RemoteSpawner = (command: string, args: string[]) => Promise<{
|
|
19
|
+
code: number;
|
|
20
|
+
stdout: string;
|
|
21
|
+
stderr: string;
|
|
22
|
+
}>;
|
|
23
|
+
export interface RemoteCommandDeps {
|
|
24
|
+
spawner?: RemoteSpawner;
|
|
25
|
+
}
|
|
26
|
+
/**
|
|
27
|
+
* `amux remote install <host> [--mode ssh|docker|k8s|local] [--harness <agent>]`
|
|
28
|
+
* `amux remote update <host> ...`
|
|
29
|
+
*/
|
|
30
|
+
export declare function remoteCommand(_client: AgentMuxClient, args: ParsedArgs, deps?: RemoteCommandDeps): Promise<number>;
|
|
31
|
+
//# sourceMappingURL=remote.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"remote.d.ts","sourceRoot":"","sources":["../../src/commands/remote.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;GAYG;AAIH,OAAO,KAAK,EACV,cAAc,EAGf,MAAM,wBAAwB,CAAC;AAGhC,OAAO,KAAK,EAAE,UAAU,EAAE,OAAO,EAAE,MAAM,kBAAkB,CAAC;AAK5D,eAAO,MAAM,YAAY,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAUhD,CAAC;AAEF,wEAAwE;AACxE,MAAM,MAAM,aAAa,GAAG,CAC1B,OAAO,EAAE,MAAM,EACf,IAAI,EAAE,MAAM,EAAE,KACX,OAAO,CAAC;IAAE,IAAI,EAAE,MAAM,CAAC;IAAC,MAAM,EAAE,MAAM,CAAC;IAAC,MAAM,EAAE,MAAM,CAAA;CAAE,CAAC,CAAC;AAmB/D,MAAM,WAAW,iBAAiB;IAChC,OAAO,CAAC,EAAE,aAAa,CAAC;CACzB;AAmDD;;;GAGG;AACH,wBAAsB,aAAa,CACjC,OAAO,EAAE,cAAc,EACvB,IAAI,EAAE,UAAU,EAChB,IAAI,GAAE,iBAAsB,GAC3B,OAAO,CAAC,MAAM,CAAC,CA6GjB"}
|
|
@@ -0,0 +1,204 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* `amux remote install <host>` / `amux remote update <host>`.
|
|
3
|
+
*
|
|
4
|
+
* Self-install pipeline — uses `buildInvocationCommand()` to build each step
|
|
5
|
+
* so the transport (ssh/docker/k8s) is selectable via `--mode` and works
|
|
6
|
+
* uniformly across environments.
|
|
7
|
+
*
|
|
8
|
+
* Steps:
|
|
9
|
+
* 1. Probe: `amux --version` — check if amux is on the remote.
|
|
10
|
+
* 2. Install: `npm install -g @a5c-ai/agent-mux-cli` if missing (or --force).
|
|
11
|
+
* 3. Harness: `amux install <harness>` — deploy the desired harness.
|
|
12
|
+
* 4. Verify: `amux detect --all --json` — confirm the harness is active.
|
|
13
|
+
*/
|
|
14
|
+
import { spawn } from 'node:child_process';
|
|
15
|
+
import { buildInvocationCommand } from '@a5c-ai/agent-mux-core';
|
|
16
|
+
import { flagBool, flagStr } from '../parse-args.js';
|
|
17
|
+
import { ExitCode } from '../exit-codes.js';
|
|
18
|
+
import { printJsonOk, printJsonError, printError } from '../output.js';
|
|
19
|
+
export const REMOTE_FLAGS = {
|
|
20
|
+
'mode': { type: 'string' }, // ssh | docker | k8s | local
|
|
21
|
+
'harness': { type: 'string' }, // agent to install (default: claude)
|
|
22
|
+
'image': { type: 'string' }, // docker image
|
|
23
|
+
'identity-file': { type: 'string' }, // ssh key
|
|
24
|
+
'port': { type: 'number' }, // ssh port
|
|
25
|
+
'namespace': { type: 'string' }, // k8s namespace
|
|
26
|
+
'context': { type: 'string' }, // k8s context
|
|
27
|
+
'force': { type: 'boolean' },
|
|
28
|
+
'dry-run': { type: 'boolean' },
|
|
29
|
+
};
|
|
30
|
+
const defaultSpawner = (command, args) => new Promise((resolve, reject) => {
|
|
31
|
+
const child = spawn(command, args, {
|
|
32
|
+
stdio: ['ignore', 'pipe', 'pipe'],
|
|
33
|
+
shell: false,
|
|
34
|
+
windowsHide: true,
|
|
35
|
+
});
|
|
36
|
+
let stdout = '';
|
|
37
|
+
let stderr = '';
|
|
38
|
+
child.stdout?.setEncoding('utf8');
|
|
39
|
+
child.stderr?.setEncoding('utf8');
|
|
40
|
+
child.stdout?.on('data', (c) => { stdout += c; });
|
|
41
|
+
child.stderr?.on('data', (c) => { stderr += c; });
|
|
42
|
+
child.on('error', (err) => reject(err));
|
|
43
|
+
child.on('exit', (code) => resolve({ code: code ?? 1, stdout, stderr }));
|
|
44
|
+
});
|
|
45
|
+
/** Build a SpawnArgs shell for a given amux (or npm) command. */
|
|
46
|
+
function makeSpawnArgs(command, args, cwd) {
|
|
47
|
+
return { command, args, env: {}, cwd, usePty: false };
|
|
48
|
+
}
|
|
49
|
+
/**
|
|
50
|
+
* Resolve the InvocationMode for a given CLI invocation of `amux remote`.
|
|
51
|
+
* The first positional after the subcommand is typically the host (for ssh)
|
|
52
|
+
* or is ignored for docker/k8s/local (which read image/namespace from flags).
|
|
53
|
+
*/
|
|
54
|
+
function buildMode(modeFlag, host, args) {
|
|
55
|
+
switch (modeFlag) {
|
|
56
|
+
case 'local':
|
|
57
|
+
return { mode: 'local' };
|
|
58
|
+
case 'docker': {
|
|
59
|
+
const image = flagStr(args.flags, 'image');
|
|
60
|
+
if (!image)
|
|
61
|
+
throw new Error('--mode=docker requires --image=<image>');
|
|
62
|
+
return { mode: 'docker', image };
|
|
63
|
+
}
|
|
64
|
+
case 'k8s': {
|
|
65
|
+
const ns = flagStr(args.flags, 'namespace');
|
|
66
|
+
const ctx = flagStr(args.flags, 'context');
|
|
67
|
+
const m = {
|
|
68
|
+
mode: 'k8s',
|
|
69
|
+
...(ns !== undefined ? { namespace: ns } : {}),
|
|
70
|
+
...(ctx !== undefined ? { context: ctx } : {}),
|
|
71
|
+
};
|
|
72
|
+
return m;
|
|
73
|
+
}
|
|
74
|
+
case 'ssh':
|
|
75
|
+
default: {
|
|
76
|
+
if (!host)
|
|
77
|
+
throw new Error('ssh mode requires a <host> positional argument');
|
|
78
|
+
const port = flagStr(args.flags, 'port');
|
|
79
|
+
const id = flagStr(args.flags, 'identity-file');
|
|
80
|
+
const m = {
|
|
81
|
+
mode: 'ssh',
|
|
82
|
+
host,
|
|
83
|
+
...(port !== undefined ? { port: Number(port) } : {}),
|
|
84
|
+
...(id !== undefined ? { identityFile: id } : {}),
|
|
85
|
+
};
|
|
86
|
+
return m;
|
|
87
|
+
}
|
|
88
|
+
}
|
|
89
|
+
}
|
|
90
|
+
/**
|
|
91
|
+
* `amux remote install <host> [--mode ssh|docker|k8s|local] [--harness <agent>]`
|
|
92
|
+
* `amux remote update <host> ...`
|
|
93
|
+
*/
|
|
94
|
+
export async function remoteCommand(_client, args, deps = {}) {
|
|
95
|
+
const jsonMode = flagBool(args.flags, 'json') === true;
|
|
96
|
+
const spawner = deps.spawner ?? defaultSpawner;
|
|
97
|
+
const sub = args.subcommand ?? args.positionals[0];
|
|
98
|
+
if (sub !== 'install' && sub !== 'update') {
|
|
99
|
+
const msg = 'Usage: amux remote install <host> [--mode ssh|docker|k8s] [--harness <agent>]';
|
|
100
|
+
if (jsonMode)
|
|
101
|
+
printJsonError('VALIDATION_ERROR', msg);
|
|
102
|
+
else
|
|
103
|
+
printError(msg);
|
|
104
|
+
return ExitCode.USAGE_ERROR;
|
|
105
|
+
}
|
|
106
|
+
// Positional order: `remote install <host>` — when parser assigned `sub` as
|
|
107
|
+
// subcommand the host is positionals[0]; when it put `install` in positionals[0]
|
|
108
|
+
// the host is positionals[1].
|
|
109
|
+
const host = args.subcommand === sub ? args.positionals[0] : args.positionals[1];
|
|
110
|
+
const modeFlag = flagStr(args.flags, 'mode') ?? 'ssh';
|
|
111
|
+
const harness = flagStr(args.flags, 'harness') ?? 'claude';
|
|
112
|
+
const force = flagBool(args.flags, 'force') === true;
|
|
113
|
+
const dryRun = flagBool(args.flags, 'dry-run') === true;
|
|
114
|
+
let invocation;
|
|
115
|
+
try {
|
|
116
|
+
invocation = buildMode(modeFlag, host, args);
|
|
117
|
+
}
|
|
118
|
+
catch (err) {
|
|
119
|
+
const msg = err instanceof Error ? err.message : String(err);
|
|
120
|
+
if (jsonMode)
|
|
121
|
+
printJsonError('VALIDATION_ERROR', msg);
|
|
122
|
+
else
|
|
123
|
+
printError(msg);
|
|
124
|
+
return ExitCode.USAGE_ERROR;
|
|
125
|
+
}
|
|
126
|
+
const cwd = process.cwd();
|
|
127
|
+
const steps = [];
|
|
128
|
+
const runStep = async (step, cmd, cmdArgs) => {
|
|
129
|
+
const spawnArgs = makeSpawnArgs(cmd, cmdArgs, cwd);
|
|
130
|
+
const inv = buildInvocationCommand(invocation, spawnArgs, 'agent-mux-remote');
|
|
131
|
+
const entry = { step, command: inv.command, args: inv.args };
|
|
132
|
+
steps.push(entry);
|
|
133
|
+
if (dryRun) {
|
|
134
|
+
entry.result = { code: 0, stdout: '', stderr: '' };
|
|
135
|
+
if (!jsonMode)
|
|
136
|
+
process.stdout.write(`[dry-run] ${inv.command} ${inv.args.join(' ')}\n`);
|
|
137
|
+
return entry.result;
|
|
138
|
+
}
|
|
139
|
+
if (!jsonMode)
|
|
140
|
+
process.stdout.write(`=> ${step}: ${inv.command} ${inv.args.slice(0, 6).join(' ')}${inv.args.length > 6 ? ' ...' : ''}\n`);
|
|
141
|
+
const r = await spawner(inv.command, inv.args);
|
|
142
|
+
entry.result = r;
|
|
143
|
+
return r;
|
|
144
|
+
};
|
|
145
|
+
// Step 1: probe amux
|
|
146
|
+
const probe = await runStep('probe', 'amux', ['--version']);
|
|
147
|
+
const needsInstall = sub === 'update' || probe.code !== 0 || force;
|
|
148
|
+
// Step 2: install amux itself if missing (or forced / update)
|
|
149
|
+
if (needsInstall) {
|
|
150
|
+
const npmVerb = sub === 'update' ? 'update' : 'install';
|
|
151
|
+
const npm = await runStep('amux-self', 'npm', [npmVerb, '-g', '@a5c-ai/agent-mux-cli']);
|
|
152
|
+
if (!dryRun && npm.code !== 0) {
|
|
153
|
+
const msg = `npm ${npmVerb} failed on remote (code ${npm.code})`;
|
|
154
|
+
if (jsonMode)
|
|
155
|
+
printJsonError('INTERNAL', msg);
|
|
156
|
+
else
|
|
157
|
+
printError(msg);
|
|
158
|
+
if (!jsonMode && npm.stderr)
|
|
159
|
+
process.stderr.write(npm.stderr);
|
|
160
|
+
return ExitCode.GENERAL_ERROR;
|
|
161
|
+
}
|
|
162
|
+
}
|
|
163
|
+
// Step 3: install harness
|
|
164
|
+
const harnessVerb = sub === 'update' ? 'update' : 'install';
|
|
165
|
+
const installArgs = [harnessVerb, harness];
|
|
166
|
+
if (force && sub === 'install')
|
|
167
|
+
installArgs.push('--force');
|
|
168
|
+
const hres = await runStep('harness', 'amux', installArgs);
|
|
169
|
+
if (!dryRun && hres.code !== 0) {
|
|
170
|
+
const msg = `amux ${harnessVerb} ${harness} failed on remote (code ${hres.code})`;
|
|
171
|
+
if (jsonMode)
|
|
172
|
+
printJsonError('INTERNAL', msg);
|
|
173
|
+
else
|
|
174
|
+
printError(msg);
|
|
175
|
+
if (!jsonMode && hres.stderr)
|
|
176
|
+
process.stderr.write(hres.stderr);
|
|
177
|
+
return ExitCode.GENERAL_ERROR;
|
|
178
|
+
}
|
|
179
|
+
// Step 4: verify
|
|
180
|
+
const verify = await runStep('verify', 'amux', ['detect', '--all', '--json']);
|
|
181
|
+
if (jsonMode) {
|
|
182
|
+
printJsonOk({
|
|
183
|
+
host: host ?? null,
|
|
184
|
+
mode: modeFlag,
|
|
185
|
+
harness,
|
|
186
|
+
subcommand: sub,
|
|
187
|
+
dryRun: dryRun || undefined,
|
|
188
|
+
steps: steps.map((s) => ({
|
|
189
|
+
step: s.step,
|
|
190
|
+
command: s.command,
|
|
191
|
+
args: s.args,
|
|
192
|
+
code: s.result?.code ?? null,
|
|
193
|
+
stdout: s.result?.stdout ?? '',
|
|
194
|
+
stderr: s.result?.stderr ?? '',
|
|
195
|
+
})),
|
|
196
|
+
});
|
|
197
|
+
}
|
|
198
|
+
else {
|
|
199
|
+
process.stdout.write(`\n${sub === 'update' ? 'Updated' : 'Installed'} ${harness} on ${host ?? modeFlag} (mode=${modeFlag}).\n` +
|
|
200
|
+
(verify.stdout ? `\nVerify output:\n${verify.stdout}\n` : ''));
|
|
201
|
+
}
|
|
202
|
+
return ExitCode.SUCCESS;
|
|
203
|
+
}
|
|
204
|
+
//# sourceMappingURL=remote.js.map
|