anpm-io 1.0.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/README.md +174 -0
- package/dist/commands/access.d.ts +2 -0
- package/dist/commands/access.js +90 -0
- package/dist/commands/adopt.d.ts +2 -0
- package/dist/commands/adopt.js +177 -0
- package/dist/commands/changelog.d.ts +2 -0
- package/dist/commands/changelog.js +67 -0
- package/dist/commands/check-update.d.ts +2 -0
- package/dist/commands/check-update.js +76 -0
- package/dist/commands/config.d.ts +2 -0
- package/dist/commands/config.js +84 -0
- package/dist/commands/create.d.ts +2 -0
- package/dist/commands/create.js +227 -0
- package/dist/commands/deploy-record.d.ts +2 -0
- package/dist/commands/deploy-record.js +93 -0
- package/dist/commands/deploy.d.ts +2 -0
- package/dist/commands/deploy.js +284 -0
- package/dist/commands/diff.d.ts +2 -0
- package/dist/commands/diff.js +92 -0
- package/dist/commands/feedback.d.ts +2 -0
- package/dist/commands/feedback.js +71 -0
- package/dist/commands/grant.d.ts +33 -0
- package/dist/commands/grant.js +190 -0
- package/dist/commands/hub.d.ts +2 -0
- package/dist/commands/hub.js +171 -0
- package/dist/commands/init.d.ts +13 -0
- package/dist/commands/init.js +172 -0
- package/dist/commands/install.d.ts +2 -0
- package/dist/commands/install.js +626 -0
- package/dist/commands/join.d.ts +6 -0
- package/dist/commands/join.js +90 -0
- package/dist/commands/link.d.ts +2 -0
- package/dist/commands/link.js +112 -0
- package/dist/commands/list.d.ts +2 -0
- package/dist/commands/list.js +144 -0
- package/dist/commands/login.d.ts +7 -0
- package/dist/commands/login.js +235 -0
- package/dist/commands/orgs.d.ts +10 -0
- package/dist/commands/orgs.js +128 -0
- package/dist/commands/outdated.d.ts +2 -0
- package/dist/commands/outdated.js +70 -0
- package/dist/commands/package.d.ts +57 -0
- package/dist/commands/package.js +569 -0
- package/dist/commands/ping.d.ts +2 -0
- package/dist/commands/ping.js +40 -0
- package/dist/commands/publish.d.ts +98 -0
- package/dist/commands/publish.js +899 -0
- package/dist/commands/run.d.ts +2 -0
- package/dist/commands/run.js +249 -0
- package/dist/commands/search.d.ts +2 -0
- package/dist/commands/search.js +57 -0
- package/dist/commands/status.d.ts +2 -0
- package/dist/commands/status.js +159 -0
- package/dist/commands/uninstall.d.ts +2 -0
- package/dist/commands/uninstall.js +132 -0
- package/dist/commands/update.d.ts +2 -0
- package/dist/commands/update.js +171 -0
- package/dist/commands/versions.d.ts +2 -0
- package/dist/commands/versions.js +44 -0
- package/dist/index.d.ts +2 -0
- package/dist/index.js +91 -0
- package/dist/lib/agent-status.d.ts +23 -0
- package/dist/lib/agent-status.js +127 -0
- package/dist/lib/ai-tools.d.ts +34 -0
- package/dist/lib/ai-tools.js +104 -0
- package/dist/lib/anpm-config.d.ts +39 -0
- package/dist/lib/anpm-config.js +112 -0
- package/dist/lib/api.d.ts +24 -0
- package/dist/lib/api.js +151 -0
- package/dist/lib/auto-detect.d.ts +30 -0
- package/dist/lib/auto-detect.js +112 -0
- package/dist/lib/cloud-providers/anthropic.d.ts +19 -0
- package/dist/lib/cloud-providers/anthropic.js +200 -0
- package/dist/lib/cloud-providers/package-mapper.d.ts +9 -0
- package/dist/lib/cloud-providers/package-mapper.js +34 -0
- package/dist/lib/cloud-providers/provider.d.ts +60 -0
- package/dist/lib/cloud-providers/provider.js +7 -0
- package/dist/lib/command-adapter.d.ts +41 -0
- package/dist/lib/command-adapter.js +188 -0
- package/dist/lib/config.d.ts +50 -0
- package/dist/lib/config.js +274 -0
- package/dist/lib/contact-format.d.ts +7 -0
- package/dist/lib/contact-format.js +23 -0
- package/dist/lib/device-hash.d.ts +1 -0
- package/dist/lib/device-hash.js +16 -0
- package/dist/lib/error-report.d.ts +5 -0
- package/dist/lib/error-report.js +28 -0
- package/dist/lib/git-installer.d.ts +16 -0
- package/dist/lib/git-installer.js +97 -0
- package/dist/lib/git-operations.d.ts +38 -0
- package/dist/lib/git-operations.js +183 -0
- package/dist/lib/hub-notify.d.ts +9 -0
- package/dist/lib/hub-notify.js +66 -0
- package/dist/lib/install-source.d.ts +33 -0
- package/dist/lib/install-source.js +98 -0
- package/dist/lib/installer.d.ts +40 -0
- package/dist/lib/installer.js +358 -0
- package/dist/lib/local-installer.d.ts +15 -0
- package/dist/lib/local-installer.js +73 -0
- package/dist/lib/lockfile.d.ts +13 -0
- package/dist/lib/lockfile.js +42 -0
- package/dist/lib/manifest.d.ts +65 -0
- package/dist/lib/manifest.js +113 -0
- package/dist/lib/migration.d.ts +10 -0
- package/dist/lib/migration.js +91 -0
- package/dist/lib/paths.d.ts +10 -0
- package/dist/lib/paths.js +22 -0
- package/dist/lib/preamble.d.ts +22 -0
- package/dist/lib/preamble.js +133 -0
- package/dist/lib/relay-config.d.ts +13 -0
- package/dist/lib/relay-config.js +46 -0
- package/dist/lib/requires-suggest.d.ts +23 -0
- package/dist/lib/requires-suggest.js +295 -0
- package/dist/lib/setup-command.d.ts +6 -0
- package/dist/lib/setup-command.js +72 -0
- package/dist/lib/slug.d.ts +24 -0
- package/dist/lib/slug.js +100 -0
- package/dist/lib/step-tracker.d.ts +8 -0
- package/dist/lib/step-tracker.js +28 -0
- package/dist/lib/storage.d.ts +6 -0
- package/dist/lib/storage.js +23 -0
- package/dist/lib/update-cache.d.ts +2 -0
- package/dist/lib/update-cache.js +51 -0
- package/dist/lib/version-check.d.ts +10 -0
- package/dist/lib/version-check.js +75 -0
- package/dist/mcp/server.d.ts +3 -0
- package/dist/mcp/server.js +112 -0
- package/dist/postinstall.d.ts +8 -0
- package/dist/postinstall.js +41 -0
- package/dist/prompts/_error-handling.md +38 -0
- package/dist/prompts/create.md +170 -0
- package/dist/prompts/explore.md +30 -0
- package/dist/prompts/index.d.ts +3 -0
- package/dist/prompts/index.js +22 -0
- package/dist/relay-compat.d.ts +2 -0
- package/dist/relay-compat.js +7 -0
- package/dist/types.d.ts +118 -0
- package/dist/types.js +2 -0
- package/package.json +51 -0
|
@@ -0,0 +1,171 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
3
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
|
+
};
|
|
5
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
|
+
exports.registerHub = registerHub;
|
|
7
|
+
const fs_1 = __importDefault(require("fs"));
|
|
8
|
+
const os_1 = __importDefault(require("os"));
|
|
9
|
+
const path_1 = __importDefault(require("path"));
|
|
10
|
+
const child_process_1 = require("child_process");
|
|
11
|
+
const HUB_STATE_PATH = path_1.default.join(os_1.default.homedir(), '.relay', 'hub', 'state.json');
|
|
12
|
+
const HUB_SERVER_SCRIPT = path_1.default.resolve(__dirname, '..', '..', '..', 'hub', 'server', 'index.ts');
|
|
13
|
+
const DEFAULT_PORT = 3847;
|
|
14
|
+
function readState() {
|
|
15
|
+
try {
|
|
16
|
+
if (!fs_1.default.existsSync(HUB_STATE_PATH))
|
|
17
|
+
return null;
|
|
18
|
+
const state = JSON.parse(fs_1.default.readFileSync(HUB_STATE_PATH, 'utf-8'));
|
|
19
|
+
// Check if process is alive
|
|
20
|
+
try {
|
|
21
|
+
process.kill(state.pid, 0);
|
|
22
|
+
return state;
|
|
23
|
+
}
|
|
24
|
+
catch {
|
|
25
|
+
// Process dead, clean up stale state
|
|
26
|
+
fs_1.default.unlinkSync(HUB_STATE_PATH);
|
|
27
|
+
return null;
|
|
28
|
+
}
|
|
29
|
+
}
|
|
30
|
+
catch {
|
|
31
|
+
return null;
|
|
32
|
+
}
|
|
33
|
+
}
|
|
34
|
+
function writeState(state) {
|
|
35
|
+
const dir = path_1.default.dirname(HUB_STATE_PATH);
|
|
36
|
+
fs_1.default.mkdirSync(dir, { recursive: true });
|
|
37
|
+
fs_1.default.writeFileSync(HUB_STATE_PATH, JSON.stringify(state, null, 2));
|
|
38
|
+
}
|
|
39
|
+
function clearState() {
|
|
40
|
+
try {
|
|
41
|
+
fs_1.default.unlinkSync(HUB_STATE_PATH);
|
|
42
|
+
}
|
|
43
|
+
catch { }
|
|
44
|
+
}
|
|
45
|
+
function findRuntime() {
|
|
46
|
+
// Use npx tsx (Node + TypeScript) — node-pty requires Node runtime
|
|
47
|
+
const tsxPath = path_1.default.join(__dirname, '..', '..', '..', 'hub', 'node_modules', '.bin', 'tsx');
|
|
48
|
+
if (fs_1.default.existsSync(tsxPath)) {
|
|
49
|
+
return { cmd: tsxPath, args: [] };
|
|
50
|
+
}
|
|
51
|
+
// Fallback: npx tsx
|
|
52
|
+
return { cmd: 'npx', args: ['tsx'] };
|
|
53
|
+
}
|
|
54
|
+
function registerHub(program) {
|
|
55
|
+
const hub = program
|
|
56
|
+
.command('hub')
|
|
57
|
+
.description('로컬 Hub GUI 서버를 관리합니다');
|
|
58
|
+
hub
|
|
59
|
+
.command('start')
|
|
60
|
+
.description('Hub 서버를 시작합니다')
|
|
61
|
+
.option('-p, --port <port>', '포트 번호', String(DEFAULT_PORT))
|
|
62
|
+
.option('--no-open', '브라우저 자동 열기 비활성화')
|
|
63
|
+
.action(async (opts) => {
|
|
64
|
+
const existing = readState();
|
|
65
|
+
if (existing) {
|
|
66
|
+
console.log(`\x1b[33mhub가 이미 실행 중입니다 (PID: ${existing.pid})\x1b[0m`);
|
|
67
|
+
console.log(` http://localhost:${existing.port}`);
|
|
68
|
+
return;
|
|
69
|
+
}
|
|
70
|
+
const port = parseInt(opts.port, 10);
|
|
71
|
+
const runtime = findRuntime();
|
|
72
|
+
// Resolve server script path
|
|
73
|
+
let serverScript = HUB_SERVER_SCRIPT;
|
|
74
|
+
if (!fs_1.default.existsSync(serverScript)) {
|
|
75
|
+
// Fallback: installed as harness
|
|
76
|
+
const harnessScript = path_1.default.join(os_1.default.homedir(), '.relay', 'agents', 'relay', 'hub', 'server', 'index.ts');
|
|
77
|
+
if (fs_1.default.existsSync(harnessScript)) {
|
|
78
|
+
serverScript = harnessScript;
|
|
79
|
+
}
|
|
80
|
+
else {
|
|
81
|
+
console.error('\x1b[31mhub 서버 스크립트를 찾을 수 없습니다.\x1b[0m');
|
|
82
|
+
console.error(` Expected: ${HUB_SERVER_SCRIPT}`);
|
|
83
|
+
process.exit(1);
|
|
84
|
+
}
|
|
85
|
+
}
|
|
86
|
+
console.log('hub 서버를 시작합니다...');
|
|
87
|
+
// Log to file for debugging
|
|
88
|
+
const logDir = path_1.default.join(os_1.default.homedir(), '.relay', 'hub');
|
|
89
|
+
fs_1.default.mkdirSync(logDir, { recursive: true });
|
|
90
|
+
const logFile = fs_1.default.openSync(path_1.default.join(logDir, 'hub.log'), 'a');
|
|
91
|
+
const child = (0, child_process_1.spawn)(runtime.cmd, [...runtime.args, serverScript], {
|
|
92
|
+
env: { ...process.env, HUB_PORT: String(port) },
|
|
93
|
+
detached: true,
|
|
94
|
+
stdio: ['ignore', logFile, logFile],
|
|
95
|
+
});
|
|
96
|
+
child.unref();
|
|
97
|
+
if (!child.pid) {
|
|
98
|
+
console.error('\x1b[31mhub 서버 시작 실패\x1b[0m');
|
|
99
|
+
process.exit(1);
|
|
100
|
+
}
|
|
101
|
+
// Wait for server to write state.json (up to 15s)
|
|
102
|
+
let state = null;
|
|
103
|
+
for (let i = 0; i < 30; i++) {
|
|
104
|
+
await new Promise((r) => setTimeout(r, 500));
|
|
105
|
+
state = readState();
|
|
106
|
+
if (state)
|
|
107
|
+
break;
|
|
108
|
+
}
|
|
109
|
+
if (!state) {
|
|
110
|
+
console.error('\x1b[31mhub 서버 시작 시간 초과\x1b[0m');
|
|
111
|
+
process.exit(1);
|
|
112
|
+
}
|
|
113
|
+
console.log(`\n \x1b[32m✓ relay hub\x1b[0m running at \x1b[36mhttp://localhost:${state.port}\x1b[0m`);
|
|
114
|
+
console.log(` PID: ${state.pid}\n`);
|
|
115
|
+
if (opts.open) {
|
|
116
|
+
try {
|
|
117
|
+
const openCmd = process.platform === 'darwin' ? 'open'
|
|
118
|
+
: process.platform === 'win32' ? 'start'
|
|
119
|
+
: 'xdg-open';
|
|
120
|
+
(0, child_process_1.execSync)(`${openCmd} http://localhost:${port}`, { stdio: 'ignore' });
|
|
121
|
+
}
|
|
122
|
+
catch { }
|
|
123
|
+
}
|
|
124
|
+
});
|
|
125
|
+
hub
|
|
126
|
+
.command('stop')
|
|
127
|
+
.description('Hub 서버를 종료합니다')
|
|
128
|
+
.action(async () => {
|
|
129
|
+
const state = readState();
|
|
130
|
+
if (!state) {
|
|
131
|
+
console.log('hub가 실행 중이 아닙니다.');
|
|
132
|
+
return;
|
|
133
|
+
}
|
|
134
|
+
try {
|
|
135
|
+
process.kill(state.pid, 'SIGTERM');
|
|
136
|
+
clearState();
|
|
137
|
+
console.log(`\x1b[32m✓ hub 종료됨\x1b[0m (PID: ${state.pid})`);
|
|
138
|
+
}
|
|
139
|
+
catch {
|
|
140
|
+
clearState();
|
|
141
|
+
console.log('hub 프로세스가 이미 종료되었습니다.');
|
|
142
|
+
}
|
|
143
|
+
});
|
|
144
|
+
hub
|
|
145
|
+
.command('status')
|
|
146
|
+
.description('Hub 서버 상태를 확인합니다')
|
|
147
|
+
.action(async () => {
|
|
148
|
+
const state = readState();
|
|
149
|
+
if (!state) {
|
|
150
|
+
console.log('hub: \x1b[2m stopped\x1b[0m');
|
|
151
|
+
return;
|
|
152
|
+
}
|
|
153
|
+
console.log(`hub: \x1b[32m● running\x1b[0m`);
|
|
154
|
+
console.log(` URL: http://localhost:${state.port}`);
|
|
155
|
+
console.log(` PID: ${state.pid}`);
|
|
156
|
+
console.log(` 시작: ${state.startedAt}`);
|
|
157
|
+
// Try to get active processes
|
|
158
|
+
try {
|
|
159
|
+
const resp = await fetch(`http://localhost:${state.port}/api/processes`);
|
|
160
|
+
const procs = await resp.json();
|
|
161
|
+
if (procs.length > 0) {
|
|
162
|
+
console.log(`\n 활성 하네스:`);
|
|
163
|
+
for (const p of procs) {
|
|
164
|
+
const dot = p.state === 'active' ? '\x1b[32m●\x1b[0m' : '\x1b[33m○\x1b[0m';
|
|
165
|
+
console.log(` ${dot} ${p.harnessName} (${p.state})`);
|
|
166
|
+
}
|
|
167
|
+
}
|
|
168
|
+
}
|
|
169
|
+
catch { }
|
|
170
|
+
});
|
|
171
|
+
}
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import { Command } from 'commander';
|
|
2
|
+
import { type AITool } from '../lib/ai-tools.js';
|
|
3
|
+
export declare function installGlobalUserCommands(overrideTools?: AITool[]): {
|
|
4
|
+
installed: boolean;
|
|
5
|
+
commands: string[];
|
|
6
|
+
tools: string[];
|
|
7
|
+
removed: string[];
|
|
8
|
+
};
|
|
9
|
+
/**
|
|
10
|
+
* 글로벌 User 커맨드가 이미 설치되어 있는지 확인한다.
|
|
11
|
+
*/
|
|
12
|
+
export declare function hasGlobalUserCommands(overrideTools?: AITool[]): boolean;
|
|
13
|
+
export declare function registerInit(program: Command): void;
|
|
@@ -0,0 +1,172 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
3
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
|
+
};
|
|
5
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
|
+
exports.installGlobalUserCommands = installGlobalUserCommands;
|
|
7
|
+
exports.hasGlobalUserCommands = hasGlobalUserCommands;
|
|
8
|
+
exports.registerInit = registerInit;
|
|
9
|
+
const fs_1 = __importDefault(require("fs"));
|
|
10
|
+
const path_1 = __importDefault(require("path"));
|
|
11
|
+
const ai_tools_js_1 = require("../lib/ai-tools.js");
|
|
12
|
+
const paths_js_1 = require("../lib/paths.js");
|
|
13
|
+
const command_adapter_js_1 = require("../lib/command-adapter.js");
|
|
14
|
+
const config_js_1 = require("../lib/config.js");
|
|
15
|
+
// eslint-disable-next-line @typescript-eslint/no-var-requires
|
|
16
|
+
const pkg = require('../../package.json');
|
|
17
|
+
function showWelcome() {
|
|
18
|
+
const lines = [
|
|
19
|
+
'',
|
|
20
|
+
' \x1b[33m⚡\x1b[0m \x1b[1manpm\x1b[0m — Agent Marketplace',
|
|
21
|
+
'',
|
|
22
|
+
' 에이전트 CLI에 anpm 커맨드를 연결합니다.',
|
|
23
|
+
'',
|
|
24
|
+
' \x1b[2mUser 커맨드 (글로벌)\x1b[0m',
|
|
25
|
+
' /relay-explore 에이전트 탐색 & 추천',
|
|
26
|
+
' /relay-create 에이전트 생성 & 배포',
|
|
27
|
+
' /relay-status 설치 현황 & Organization',
|
|
28
|
+
' /relay-uninstall 에이전트 삭제',
|
|
29
|
+
'',
|
|
30
|
+
' \x1b[2mCLI 명령어\x1b[0m',
|
|
31
|
+
' anpm install 에이전트 설치 (CLI 한 줄 완결)',
|
|
32
|
+
' anpm publish 재배포 (--patch/--minor/--major)',
|
|
33
|
+
'',
|
|
34
|
+
];
|
|
35
|
+
console.log(lines.join('\n'));
|
|
36
|
+
}
|
|
37
|
+
/**
|
|
38
|
+
* 글로벌 User 커맨드를 감지된 모든 에이전트 CLI에 설치한다.
|
|
39
|
+
* ~/{skillsDir}/commands/relay/ 에 설치.
|
|
40
|
+
* 기존 파일 중 현재 커맨드 목록에 없는 것은 제거한다.
|
|
41
|
+
*/
|
|
42
|
+
/** 제거된 레거시 커맨드 → 대체 안내 매핑 */
|
|
43
|
+
const LEGACY_COMMANDS = {
|
|
44
|
+
'relay-install': 'anpm install (CLI) 또는 /relay-explore',
|
|
45
|
+
'relay-publish': 'anpm publish --patch (CLI) 또는 /relay-create',
|
|
46
|
+
};
|
|
47
|
+
function installGlobalUserCommands(overrideTools) {
|
|
48
|
+
const globalCLIs = overrideTools ?? (0, ai_tools_js_1.detectGlobalCLIs)();
|
|
49
|
+
const currentIds = new Set(command_adapter_js_1.USER_COMMANDS.map((c) => c.id));
|
|
50
|
+
const commands = [];
|
|
51
|
+
const tools = [];
|
|
52
|
+
const removed = [];
|
|
53
|
+
const targetDirs = globalCLIs.map((t) => ({ name: t.name, dir: (0, command_adapter_js_1.getGlobalCommandDirForTool)(t.skillsDir), getPath: (id) => (0, command_adapter_js_1.getGlobalCommandPathForTool)(t.skillsDir, id) }));
|
|
54
|
+
for (const target of targetDirs) {
|
|
55
|
+
fs_1.default.mkdirSync(target.dir, { recursive: true });
|
|
56
|
+
// 기존 파일 중 현재 목록에 없는 것 제거 + 레거시 안내
|
|
57
|
+
for (const file of fs_1.default.readdirSync(target.dir)) {
|
|
58
|
+
const id = file.replace(/\.md$/, '');
|
|
59
|
+
if (!currentIds.has(id)) {
|
|
60
|
+
fs_1.default.unlinkSync(path_1.default.join(target.dir, file));
|
|
61
|
+
if (LEGACY_COMMANDS[id] && !removed.includes(id)) {
|
|
62
|
+
removed.push(id);
|
|
63
|
+
}
|
|
64
|
+
}
|
|
65
|
+
}
|
|
66
|
+
// 현재 커맨드 설치 (덮어쓰기)
|
|
67
|
+
for (const cmd of command_adapter_js_1.USER_COMMANDS) {
|
|
68
|
+
fs_1.default.writeFileSync(target.getPath(cmd.id), (0, command_adapter_js_1.formatCommandFile)(cmd));
|
|
69
|
+
}
|
|
70
|
+
tools.push(target.name);
|
|
71
|
+
}
|
|
72
|
+
for (const cmd of command_adapter_js_1.USER_COMMANDS) {
|
|
73
|
+
commands.push(cmd.id);
|
|
74
|
+
}
|
|
75
|
+
return { installed: true, commands, tools, removed };
|
|
76
|
+
}
|
|
77
|
+
/**
|
|
78
|
+
* 글로벌 User 커맨드가 이미 설치되어 있는지 확인한다.
|
|
79
|
+
*/
|
|
80
|
+
function hasGlobalUserCommands(overrideTools) {
|
|
81
|
+
if (overrideTools) {
|
|
82
|
+
return overrideTools.every((tool) => command_adapter_js_1.USER_COMMANDS.every((cmd) => fs_1.default.existsSync((0, command_adapter_js_1.getGlobalCommandPathForTool)(tool.skillsDir, cmd.id))));
|
|
83
|
+
}
|
|
84
|
+
return command_adapter_js_1.USER_COMMANDS.every((cmd) => fs_1.default.existsSync((0, command_adapter_js_1.getGlobalCommandPath)(cmd.id)));
|
|
85
|
+
}
|
|
86
|
+
function registerInit(program) {
|
|
87
|
+
program
|
|
88
|
+
.command('init')
|
|
89
|
+
.description('에이전트 CLI에 anpm 슬래시 커맨드를 설치합니다')
|
|
90
|
+
.option('--tools <tools>', '설치할 에이전트 CLI 지정 (쉼표 구분)')
|
|
91
|
+
.option('--all', '감지된 모든 에이전트 CLI에 설치')
|
|
92
|
+
.option('--auto', '대화형 프롬프트 없이 자동으로 모든 감지된 CLI에 설치')
|
|
93
|
+
.option('--project <dir>', '프로젝트 루트 경로 (기본: cwd, 환경변수: RELAY_PROJECT_PATH)')
|
|
94
|
+
.action(async (opts) => {
|
|
95
|
+
const json = program.opts().json ?? false;
|
|
96
|
+
// auto mode: --auto flag, --all flag, or stdin is not a TTY (but NOT --json alone)
|
|
97
|
+
const autoMode = opts.auto === true || opts.all === true || !process.stdin.isTTY;
|
|
98
|
+
const projectPath = (0, paths_js_1.resolveProjectPath)(opts.project);
|
|
99
|
+
const detected = (0, ai_tools_js_1.detectAgentCLIs)(projectPath);
|
|
100
|
+
// ── 0. --json 모드에서 --tools/--all 없으면 MISSING_TOOLS 에러 ──
|
|
101
|
+
if (json && !opts.tools && !opts.all && !opts.auto) {
|
|
102
|
+
const detectedOptions = detected.map((t) => ({ value: t.value, label: t.name }));
|
|
103
|
+
if (detectedOptions.length === 0) {
|
|
104
|
+
detectedOptions.push(...ai_tools_js_1.AI_TOOLS.slice(0, 5).map((t) => ({ value: t.value, label: t.name })));
|
|
105
|
+
}
|
|
106
|
+
console.error(JSON.stringify({
|
|
107
|
+
error: 'MISSING_TOOLS',
|
|
108
|
+
message: '설치할 에이전트 CLI를 선택하세요.',
|
|
109
|
+
fix: `anpm init --tools <도구1,도구2> --json 또는 anpm init --all --json`,
|
|
110
|
+
options: detectedOptions,
|
|
111
|
+
}));
|
|
112
|
+
process.exit(1);
|
|
113
|
+
}
|
|
114
|
+
// ── 1. 글로벌 User 커맨드 설치 ──
|
|
115
|
+
let globalStatus = 'already';
|
|
116
|
+
let globalTools = [];
|
|
117
|
+
let removedCommands = [];
|
|
118
|
+
{
|
|
119
|
+
const result = installGlobalUserCommands();
|
|
120
|
+
globalStatus = hasGlobalUserCommands() ? 'updated' : 'installed';
|
|
121
|
+
globalTools = result.tools;
|
|
122
|
+
removedCommands = result.removed;
|
|
123
|
+
// Register relay-core in installed.json
|
|
124
|
+
const installed = (0, config_js_1.loadInstalled)();
|
|
125
|
+
installed['relay-core'] = {
|
|
126
|
+
version: pkg.version,
|
|
127
|
+
installed_at: new Date().toISOString(),
|
|
128
|
+
files: result.commands.map((c) => (0, command_adapter_js_1.getGlobalCommandPath)(c)),
|
|
129
|
+
type: 'system',
|
|
130
|
+
};
|
|
131
|
+
(0, config_js_1.saveInstalled)(installed);
|
|
132
|
+
}
|
|
133
|
+
if (!autoMode) {
|
|
134
|
+
showWelcome();
|
|
135
|
+
}
|
|
136
|
+
// ── 2. 출력 ──
|
|
137
|
+
if (json) {
|
|
138
|
+
console.log(JSON.stringify({
|
|
139
|
+
status: 'ok',
|
|
140
|
+
global: {
|
|
141
|
+
status: globalStatus,
|
|
142
|
+
path: (0, command_adapter_js_1.getGlobalCommandDir)(),
|
|
143
|
+
commands: command_adapter_js_1.USER_COMMANDS.map((c) => c.id),
|
|
144
|
+
},
|
|
145
|
+
}));
|
|
146
|
+
}
|
|
147
|
+
else {
|
|
148
|
+
console.log(`\n\x1b[32m✓ anpm 초기화 완료\x1b[0m\n`);
|
|
149
|
+
// 레거시 커맨드 마이그레이션 안내
|
|
150
|
+
if (removedCommands.length > 0) {
|
|
151
|
+
console.log(` \x1b[33m⚠ 변경된 커맨드:\x1b[0m`);
|
|
152
|
+
for (const id of removedCommands) {
|
|
153
|
+
console.log(` \x1b[31m✗ /${id}\x1b[0m → ${LEGACY_COMMANDS[id]}`);
|
|
154
|
+
}
|
|
155
|
+
console.log();
|
|
156
|
+
}
|
|
157
|
+
// 글로벌
|
|
158
|
+
{
|
|
159
|
+
const toolNames = globalTools.length > 0 ? globalTools.join(', ') : '(감지된 CLI 없음)';
|
|
160
|
+
console.log(` \x1b[36m커맨드 (글로벌)\x1b[0m — ${globalStatus === 'updated' ? '업데이트됨' : '설치됨'}`);
|
|
161
|
+
console.log(` 감지된 CLI: \x1b[36m${toolNames}\x1b[0m`);
|
|
162
|
+
for (const cmd of command_adapter_js_1.USER_COMMANDS) {
|
|
163
|
+
console.log(` /${cmd.id}`);
|
|
164
|
+
}
|
|
165
|
+
console.log();
|
|
166
|
+
}
|
|
167
|
+
console.log(' 에이전트를 만들려면 \x1b[33manpm create <name>\x1b[0m을 사용하세요.');
|
|
168
|
+
console.log();
|
|
169
|
+
console.log(' IDE를 재시작하면 슬래시 커맨드가 활성화됩니다.');
|
|
170
|
+
}
|
|
171
|
+
});
|
|
172
|
+
}
|