@mintlify/cli 4.0.1379 → 4.0.1380

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.
@@ -0,0 +1,173 @@
1
+ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
2
+ function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
3
+ return new (P || (P = Promise))(function (resolve, reject) {
4
+ function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
5
+ function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
6
+ function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
7
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
8
+ });
9
+ };
10
+ import fs from 'fs-extra';
11
+ import path from 'path';
12
+ import { CURSOR_RULE, RULE_BODY, VSCODE_RULE } from './rule.js';
13
+ export const INDEX_MCP_URL = 'https://index.mintlify.com/mcp';
14
+ export const SERVER_NAME = 'mintlify-index';
15
+ function claudeConfigDir(ctx) {
16
+ const override = ctx.env.CLAUDE_CONFIG_DIR;
17
+ return override !== undefined && override !== '' ? override : path.join(ctx.home, '.claude');
18
+ }
19
+ function claudeGlobalConfigPath(ctx) {
20
+ const override = ctx.env.CLAUDE_CONFIG_DIR;
21
+ return override !== undefined && override !== ''
22
+ ? path.join(override, '.claude.json')
23
+ : path.join(ctx.home, '.claude.json');
24
+ }
25
+ function zedUserDir(ctx) {
26
+ if (ctx.platform === 'win32') {
27
+ const appData = ctx.env.APPDATA;
28
+ const base = appData !== undefined && appData !== '' ? appData : path.join(ctx.home, 'AppData', 'Roaming');
29
+ return path.join(base, 'Zed');
30
+ }
31
+ return path.join(ctx.home, '.config', 'zed');
32
+ }
33
+ function vscodeUserDir(ctx) {
34
+ if (ctx.platform === 'darwin') {
35
+ return path.join(ctx.home, 'Library', 'Application Support', 'Code', 'User');
36
+ }
37
+ if (ctx.platform === 'win32') {
38
+ const appData = ctx.env.APPDATA;
39
+ const base = appData !== undefined && appData !== '' ? appData : path.join(ctx.home, 'AppData', 'Roaming');
40
+ return path.join(base, 'Code', 'User');
41
+ }
42
+ return path.join(ctx.home, '.config', 'Code', 'User');
43
+ }
44
+ export const CLIENTS = {
45
+ claude: {
46
+ name: 'claude',
47
+ displayName: 'Claude Code',
48
+ format: 'json',
49
+ configKey: 'mcpServers',
50
+ globalConfigPaths: (ctx) => [claudeGlobalConfigPath(ctx)],
51
+ projectConfigPaths: (ctx) => [path.join(ctx.cwd, '.mcp.json')],
52
+ buildEntry: () => ({ type: 'http', url: INDEX_MCP_URL }),
53
+ rule: {
54
+ kind: 'file',
55
+ content: RULE_BODY,
56
+ globalPath: (ctx) => path.join(claudeConfigDir(ctx), 'rules', 'mintlify-index.md'),
57
+ projectPath: (ctx) => path.join(ctx.cwd, '.claude', 'rules', 'mintlify-index.md'),
58
+ },
59
+ detectPaths: (ctx) => [claudeConfigDir(ctx)],
60
+ },
61
+ cursor: {
62
+ name: 'cursor',
63
+ displayName: 'Cursor',
64
+ format: 'json',
65
+ configKey: 'mcpServers',
66
+ globalConfigPaths: (ctx) => [path.join(ctx.home, '.cursor', 'mcp.json')],
67
+ projectConfigPaths: (ctx) => [path.join(ctx.cwd, '.cursor', 'mcp.json')],
68
+ buildEntry: () => ({ url: INDEX_MCP_URL }),
69
+ rule: {
70
+ kind: 'file',
71
+ content: CURSOR_RULE,
72
+ globalPath: (ctx) => path.join(ctx.home, '.cursor', 'rules', 'mintlify-index.mdc'),
73
+ projectPath: (ctx) => path.join(ctx.cwd, '.cursor', 'rules', 'mintlify-index.mdc'),
74
+ },
75
+ detectPaths: (ctx) => [path.join(ctx.home, '.cursor')],
76
+ },
77
+ vscode: {
78
+ name: 'vscode',
79
+ displayName: 'VS Code',
80
+ format: 'json',
81
+ configKey: 'servers',
82
+ globalConfigPaths: (ctx) => [path.join(vscodeUserDir(ctx), 'mcp.json')],
83
+ projectConfigPaths: (ctx) => [path.join(ctx.cwd, '.vscode', 'mcp.json')],
84
+ buildEntry: () => ({ type: 'http', url: INDEX_MCP_URL }),
85
+ rule: {
86
+ kind: 'file',
87
+ content: VSCODE_RULE,
88
+ globalPath: (ctx) => path.join(vscodeUserDir(ctx), 'prompts', 'mintlify-index.instructions.md'),
89
+ projectPath: (ctx) => path.join(ctx.cwd, '.github', 'instructions', 'mintlify-index.instructions.md'),
90
+ },
91
+ detectPaths: (ctx) => [vscodeUserDir(ctx)],
92
+ },
93
+ codex: {
94
+ name: 'codex',
95
+ displayName: 'Codex',
96
+ format: 'toml',
97
+ configKey: 'mcp_servers',
98
+ globalConfigPaths: (ctx) => [path.join(ctx.home, '.codex', 'config.toml')],
99
+ projectConfigPaths: (ctx) => [path.join(ctx.cwd, '.codex', 'config.toml')],
100
+ buildEntry: () => ({ type: 'http', url: INDEX_MCP_URL }),
101
+ rule: {
102
+ kind: 'append',
103
+ content: RULE_BODY,
104
+ globalPath: (ctx) => path.join(ctx.home, '.codex', 'AGENTS.md'),
105
+ projectPath: (ctx) => path.join(ctx.cwd, 'AGENTS.md'),
106
+ },
107
+ detectPaths: (ctx) => [path.join(ctx.home, '.codex')],
108
+ },
109
+ opencode: {
110
+ name: 'opencode',
111
+ displayName: 'OpenCode',
112
+ format: 'json',
113
+ configKey: 'mcp',
114
+ globalConfigPaths: (ctx) => [path.join(ctx.home, '.config', 'opencode', 'opencode.json')],
115
+ projectConfigPaths: (ctx) => [path.join(ctx.cwd, 'opencode.json')],
116
+ buildEntry: () => ({ type: 'remote', url: INDEX_MCP_URL, enabled: true }),
117
+ rule: {
118
+ kind: 'append',
119
+ content: RULE_BODY,
120
+ globalPath: (ctx) => path.join(ctx.home, '.config', 'opencode', 'AGENTS.md'),
121
+ projectPath: (ctx) => path.join(ctx.cwd, 'AGENTS.md'),
122
+ },
123
+ detectPaths: (ctx) => [path.join(ctx.home, '.config', 'opencode')],
124
+ },
125
+ windsurf: {
126
+ name: 'windsurf',
127
+ displayName: 'Windsurf',
128
+ format: 'json',
129
+ configKey: 'mcpServers',
130
+ globalConfigPaths: (ctx) => [path.join(ctx.home, '.codeium', 'windsurf', 'mcp_config.json')],
131
+ buildEntry: () => ({ serverUrl: INDEX_MCP_URL }),
132
+ rule: {
133
+ kind: 'append',
134
+ content: RULE_BODY,
135
+ globalPath: (ctx) => path.join(ctx.home, '.codeium', 'windsurf', 'memories', 'global_rules.md'),
136
+ projectPath: (ctx) => path.join(ctx.cwd, '.windsurf', 'rules', 'mintlify-index.md'),
137
+ },
138
+ detectPaths: (ctx) => [path.join(ctx.home, '.codeium', 'windsurf')],
139
+ },
140
+ zed: {
141
+ name: 'zed',
142
+ displayName: 'Zed',
143
+ format: 'json',
144
+ configKey: 'context_servers',
145
+ globalConfigPaths: (ctx) => [path.join(zedUserDir(ctx), 'settings.json')],
146
+ projectConfigPaths: (ctx) => [path.join(ctx.cwd, '.zed', 'settings.json')],
147
+ buildEntry: () => ({ url: INDEX_MCP_URL }),
148
+ detectPaths: (ctx) => [zedUserDir(ctx)],
149
+ },
150
+ };
151
+ export const ALL_CLIENT_NAMES = [
152
+ 'claude',
153
+ 'cursor',
154
+ 'vscode',
155
+ 'codex',
156
+ 'opencode',
157
+ 'windsurf',
158
+ 'zed',
159
+ ];
160
+ export function detectClients(ctx) {
161
+ return __awaiter(this, void 0, void 0, function* () {
162
+ const detected = [];
163
+ for (const name of ALL_CLIENT_NAMES) {
164
+ for (const candidate of CLIENTS[name].detectPaths(ctx)) {
165
+ if (yield fs.pathExists(candidate)) {
166
+ detected.push(name);
167
+ break;
168
+ }
169
+ }
170
+ }
171
+ return detected;
172
+ });
173
+ }
@@ -0,0 +1,126 @@
1
+ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
2
+ function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
3
+ return new (P || (P = Promise))(function (resolve, reject) {
4
+ function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
5
+ function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
6
+ function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
7
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
8
+ });
9
+ };
10
+ import fs from 'fs-extra';
11
+ import { applyEdits, modify, parse } from 'jsonc-parser';
12
+ import path from 'path';
13
+ function isEnoent(error) {
14
+ return typeof error === 'object' && error !== null && 'code' in error && error.code === 'ENOENT';
15
+ }
16
+ export function readJsonConfig(filePath) {
17
+ return __awaiter(this, void 0, void 0, function* () {
18
+ let raw;
19
+ try {
20
+ raw = yield fs.readFile(filePath, 'utf-8');
21
+ }
22
+ catch (error) {
23
+ if (isEnoent(error)) {
24
+ return {};
25
+ }
26
+ throw error;
27
+ }
28
+ if (raw.trim() === '') {
29
+ return {};
30
+ }
31
+ const errors = [];
32
+ const parsed = parse(raw, errors, { allowTrailingComma: true });
33
+ if (errors.length > 0) {
34
+ throw new Error(`invalid JSON at ${filePath}`);
35
+ }
36
+ if (typeof parsed !== 'object' || parsed === null || Array.isArray(parsed)) {
37
+ throw new Error(`expected a JSON object at ${filePath}`);
38
+ }
39
+ return parsed;
40
+ });
41
+ }
42
+ export function mergeServerEntry(config, configKey, serverName, entry) {
43
+ const section = config[configKey];
44
+ const servers = {};
45
+ if (typeof section === 'object' && section !== null && !Array.isArray(section)) {
46
+ Object.assign(servers, section);
47
+ }
48
+ const alreadyExists = serverName in servers;
49
+ servers[serverName] = entry;
50
+ return { config: Object.assign(Object.assign({}, config), { [configKey]: servers }), alreadyExists };
51
+ }
52
+ export function writeJsonConfig(filePath, config) {
53
+ return __awaiter(this, void 0, void 0, function* () {
54
+ yield fs.mkdirp(path.dirname(filePath));
55
+ yield fs.writeFile(filePath, `${JSON.stringify(config, null, 2)}\n`);
56
+ });
57
+ }
58
+ export function writeJsonServerEntry(filePath, configKey, serverName, entry) {
59
+ return __awaiter(this, void 0, void 0, function* () {
60
+ let raw;
61
+ try {
62
+ raw = yield fs.readFile(filePath, 'utf-8');
63
+ }
64
+ catch (error) {
65
+ if (!isEnoent(error)) {
66
+ throw error;
67
+ }
68
+ }
69
+ if (raw === undefined || raw.trim() === '') {
70
+ const { config } = mergeServerEntry({}, configKey, serverName, entry);
71
+ yield writeJsonConfig(filePath, config);
72
+ return { status: 'configured' };
73
+ }
74
+ const errors = [];
75
+ const parsed = parse(raw, errors, { allowTrailingComma: true });
76
+ if (errors.length > 0 || typeof parsed !== 'object' || parsed === null || Array.isArray(parsed)) {
77
+ throw new Error(`unable to parse existing config at ${filePath}`);
78
+ }
79
+ const section = parsed[configKey];
80
+ const sectionIsObject = typeof section === 'object' && section !== null && !Array.isArray(section);
81
+ const alreadyExists = sectionIsObject && serverName in section;
82
+ const edits = sectionIsObject
83
+ ? modify(raw, [configKey, serverName], entry, {
84
+ formattingOptions: { insertSpaces: true, tabSize: 2 },
85
+ })
86
+ : modify(raw, [configKey], { [serverName]: entry }, {
87
+ formattingOptions: { insertSpaces: true, tabSize: 2 },
88
+ });
89
+ yield fs.mkdirp(path.dirname(filePath));
90
+ yield fs.writeFile(filePath, applyEdits(raw, edits));
91
+ return { status: alreadyExists ? 'reconfigured' : 'configured' };
92
+ });
93
+ }
94
+ export function resolveConfigPath(candidates) {
95
+ return __awaiter(this, void 0, void 0, function* () {
96
+ for (const candidate of candidates) {
97
+ if (yield fs.pathExists(candidate)) {
98
+ return candidate;
99
+ }
100
+ }
101
+ const fallback = candidates[0];
102
+ if (fallback === undefined) {
103
+ throw new Error('no config path candidates');
104
+ }
105
+ return fallback;
106
+ });
107
+ }
108
+ export function upsertTomlServer(content, serverName, entry) {
109
+ const header = `[mcp_servers.${serverName}]`;
110
+ const escapedName = serverName.replace(/[.*+?^${}()|[\]\\]/g, '\\$&');
111
+ const headerPattern = new RegExp(`^[ \\t]*\\[mcp_servers\\.${escapedName}\\][ \\t]*(?:#.*)?$`, 'm');
112
+ const lines = Object.entries(entry).map(([key, value]) => `${key} = ${JSON.stringify(value)}`);
113
+ const block = `${[header, ...lines].join('\n')}\n`;
114
+ const match = headerPattern.exec(content);
115
+ if (match === null) {
116
+ const separator = content.length === 0 ? '' : content.endsWith('\n') ? '\n' : '\n\n';
117
+ return { content: `${content}${separator}${block}`, alreadyExists: false };
118
+ }
119
+ const headerIndex = match.index + match[0].indexOf('[');
120
+ const rest = content.slice(headerIndex + header.length);
121
+ const nextTable = rest.search(/\n\s*\[/);
122
+ const end = nextTable === -1 ? content.length : headerIndex + header.length + nextTable + 1;
123
+ const before = content.slice(0, headerIndex);
124
+ const after = content.slice(end).replace(/^\n+/, '\n');
125
+ return { content: `${before}${block}${after}`, alreadyExists: true };
126
+ }
@@ -0,0 +1,92 @@
1
+ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
2
+ function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
3
+ return new (P || (P = Promise))(function (resolve, reject) {
4
+ function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
5
+ function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
6
+ function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
7
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
8
+ });
9
+ };
10
+ import fs from 'fs-extra';
11
+ import path from 'path';
12
+ import { SERVER_NAME, } from './clients.js';
13
+ import { resolveConfigPath, upsertTomlServer, writeJsonServerEntry } from './configFile.js';
14
+ import { appendRuleSection, writeRuleFile } from './rule.js';
15
+ function writeMcpEntry(definition, scope, ctx) {
16
+ return __awaiter(this, void 0, void 0, function* () {
17
+ var _a, _b;
18
+ const projectPaths = (_b = (_a = definition.projectConfigPaths) === null || _a === void 0 ? void 0 : _a.call(definition, ctx)) !== null && _b !== void 0 ? _b : [];
19
+ const candidates = scope === 'project' && projectPaths.length > 0
20
+ ? projectPaths
21
+ : definition.globalConfigPaths(ctx);
22
+ const configPath = yield resolveConfigPath(candidates);
23
+ if (definition.format === 'toml') {
24
+ let existing = '';
25
+ try {
26
+ existing = yield fs.readFile(configPath, 'utf-8');
27
+ }
28
+ catch (error) {
29
+ if (!(typeof error === 'object' && error !== null && 'code' in error && error.code === 'ENOENT')) {
30
+ throw error;
31
+ }
32
+ }
33
+ const entry = {};
34
+ for (const [key, value] of Object.entries(definition.buildEntry())) {
35
+ if (typeof value === 'string') {
36
+ entry[key] = value;
37
+ }
38
+ }
39
+ const { content, alreadyExists } = upsertTomlServer(existing, SERVER_NAME, entry);
40
+ yield fs.mkdirp(path.dirname(configPath));
41
+ yield fs.writeFile(configPath, content);
42
+ return { status: alreadyExists ? 'reconfigured' : 'configured', configPath };
43
+ }
44
+ const { status } = yield writeJsonServerEntry(configPath, definition.configKey, SERVER_NAME, definition.buildEntry());
45
+ return { status, configPath };
46
+ });
47
+ }
48
+ function writeRule(definition, scope, ctx) {
49
+ return __awaiter(this, void 0, void 0, function* () {
50
+ var _a;
51
+ const rule = definition.rule;
52
+ if (rule === undefined) {
53
+ return { status: 'none', rulePath: '' };
54
+ }
55
+ const projectPath = (_a = rule.projectPath) === null || _a === void 0 ? void 0 : _a.call(rule, ctx);
56
+ const rulePath = scope === 'project' && projectPath !== undefined ? projectPath : rule.globalPath(ctx);
57
+ const status = rule.kind === 'file'
58
+ ? yield writeRuleFile(rulePath, rule.content)
59
+ : yield appendRuleSection(rulePath, rule.content);
60
+ return { status, rulePath };
61
+ });
62
+ }
63
+ export function setupClient(definition, scope, ctx) {
64
+ return __awaiter(this, void 0, void 0, function* () {
65
+ const result = {
66
+ client: definition.name,
67
+ displayName: definition.displayName,
68
+ mcpStatus: 'failed',
69
+ mcpDetail: '',
70
+ ruleStatus: 'none',
71
+ ruleDetail: '',
72
+ };
73
+ try {
74
+ const { status, configPath } = yield writeMcpEntry(definition, scope, ctx);
75
+ result.mcpStatus = status;
76
+ result.mcpDetail = configPath;
77
+ }
78
+ catch (error) {
79
+ result.mcpDetail = error instanceof Error ? error.message : String(error);
80
+ }
81
+ try {
82
+ const { status, rulePath } = yield writeRule(definition, scope, ctx);
83
+ result.ruleStatus = status;
84
+ result.ruleDetail = rulePath;
85
+ }
86
+ catch (error) {
87
+ result.ruleStatus = 'failed';
88
+ result.ruleDetail = error instanceof Error ? error.message : String(error);
89
+ }
90
+ return result;
91
+ });
92
+ }
@@ -0,0 +1,56 @@
1
+ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
2
+ function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
3
+ return new (P || (P = Promise))(function (resolve, reject) {
4
+ function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
5
+ function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
6
+ function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
7
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
8
+ });
9
+ };
10
+ import fs from 'fs-extra';
11
+ import path from 'path';
12
+ export const RULE_MARKER = '<!-- mintlify-index -->';
13
+ export const RULE_BODY = `Use the Mintlify index \`context\` tool whenever you research how to use a library, framework, SDK, API, or CLI tool, including syntax, configuration, migration, and setup questions. Use it even for well-known libraries, since training data may be stale, and prefer it over web search for developer documentation. Do not use it for general programming concepts or for debugging business logic.
14
+ `;
15
+ export const CURSOR_RULE = `---
16
+ alwaysApply: true
17
+ ---
18
+
19
+ ${RULE_BODY}`;
20
+ export const VSCODE_RULE = `---
21
+ applyTo: '**'
22
+ ---
23
+
24
+ ${RULE_BODY}`;
25
+ export function writeRuleFile(filePath, content) {
26
+ return __awaiter(this, void 0, void 0, function* () {
27
+ const exists = yield fs.pathExists(filePath);
28
+ yield fs.mkdirp(path.dirname(filePath));
29
+ yield fs.writeFile(filePath, content);
30
+ return exists ? 'updated' : 'installed';
31
+ });
32
+ }
33
+ export function appendRuleSection(filePath, content) {
34
+ return __awaiter(this, void 0, void 0, function* () {
35
+ const section = `${RULE_MARKER}\n${content}${RULE_MARKER}`;
36
+ let existing = '';
37
+ try {
38
+ existing = yield fs.readFile(filePath, 'utf-8');
39
+ }
40
+ catch (error) {
41
+ if (!(typeof error === 'object' && error !== null && 'code' in error && error.code === 'ENOENT')) {
42
+ throw error;
43
+ }
44
+ }
45
+ const escaped = RULE_MARKER.replace(/[.*+?^${}()|[\]\\]/g, '\\$&');
46
+ const pattern = new RegExp(`${escaped}\\n[\\s\\S]*?${escaped}`);
47
+ if (pattern.test(existing)) {
48
+ yield fs.writeFile(filePath, existing.replace(pattern, section));
49
+ return 'updated';
50
+ }
51
+ const separator = existing.length === 0 ? '' : existing.endsWith('\n') ? '\n' : '\n\n';
52
+ yield fs.mkdirp(path.dirname(filePath));
53
+ yield fs.writeFile(filePath, `${existing}${separator}${section}\n`);
54
+ return 'installed';
55
+ });
56
+ }
@@ -0,0 +1,94 @@
1
+ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
2
+ function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
3
+ return new (P || (P = Promise))(function (resolve, reject) {
4
+ function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
5
+ function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
6
+ function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
7
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
8
+ });
9
+ };
10
+ import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
11
+ import { checkbox } from '@inquirer/prompts';
12
+ import { addLog, ErrorLog, WarningLog } from '@mintlify/previewing';
13
+ import { Text } from 'ink';
14
+ import os from 'os';
15
+ import { trackEvent } from '../telemetry/track.js';
16
+ import { ALL_CLIENT_NAMES, CLIENTS, detectClients, } from './clients.js';
17
+ import { setupClient } from './engine.js';
18
+ export function resolveExplicitClients(options) {
19
+ return ALL_CLIENT_NAMES.filter((name) => options[name] === true);
20
+ }
21
+ function promptClients(detected) {
22
+ return __awaiter(this, void 0, void 0, function* () {
23
+ try {
24
+ return yield checkbox({
25
+ message: 'Which coding agents do you want to set up?',
26
+ loop: false,
27
+ choices: ALL_CLIENT_NAMES.map((name) => ({
28
+ name: CLIENTS[name].displayName,
29
+ value: name,
30
+ checked: detected.includes(name),
31
+ })),
32
+ });
33
+ }
34
+ catch (_a) {
35
+ return undefined;
36
+ }
37
+ });
38
+ }
39
+ function logResult(result) {
40
+ addLog(_jsx(Text, { bold: true, children: result.displayName }));
41
+ if (result.mcpStatus === 'failed') {
42
+ addLog(_jsx(ErrorLog, { message: ` MCP server failed: ${result.mcpDetail}` }));
43
+ }
44
+ else {
45
+ addLog(_jsxs(Text, { children: [' ', "MCP server ", result.mcpStatus, " ", _jsx(Text, { dimColor: true, children: result.mcpDetail })] }));
46
+ }
47
+ if (result.ruleStatus === 'failed') {
48
+ addLog(_jsx(ErrorLog, { message: ` Rule failed: ${result.ruleDetail}` }));
49
+ }
50
+ else if (result.ruleStatus !== 'none') {
51
+ addLog(_jsxs(Text, { children: [' ', "Rule ", result.ruleStatus, " ", _jsx(Text, { dimColor: true, children: result.ruleDetail })] }));
52
+ }
53
+ }
54
+ export function runIndexSetup(options) {
55
+ return __awaiter(this, void 0, void 0, function* () {
56
+ const ctx = {
57
+ home: os.homedir(),
58
+ cwd: process.cwd(),
59
+ platform: process.platform,
60
+ env: process.env,
61
+ };
62
+ const scope = options.project === true ? 'project' : 'global';
63
+ let selected = resolveExplicitClients(options);
64
+ if (selected.length === 0) {
65
+ const detected = yield detectClients(ctx);
66
+ if (options.yes === true) {
67
+ if (detected.length === 0) {
68
+ addLog(_jsx(ErrorLog, { message: "no coding agents detected; pass flags like --claude or --cursor" }));
69
+ return 1;
70
+ }
71
+ selected = detected;
72
+ }
73
+ else {
74
+ const picked = yield promptClients(detected);
75
+ if (picked === undefined || picked.length === 0) {
76
+ addLog(_jsx(WarningLog, { message: "setup cancelled" }));
77
+ return 1;
78
+ }
79
+ selected = picked;
80
+ }
81
+ }
82
+ const results = [];
83
+ for (const name of selected) {
84
+ results.push(yield setupClient(CLIENTS[name], scope, ctx));
85
+ }
86
+ for (const result of results) {
87
+ logResult(result);
88
+ }
89
+ const succeeded = results.filter((result) => result.mcpStatus !== 'failed');
90
+ addLog(_jsxs(Text, { children: ["Mintlify index MCP set up for ", succeeded.length, "/", results.length, " agents"] }));
91
+ void trackEvent('cli.index.completed', { clients: selected, scope });
92
+ return succeeded.length > 0 ? 0 : 1;
93
+ });
94
+ }