harmony-mcp 1.3.1 → 1.3.3
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 +64 -39
- package/dist/cli.js +1663 -78
- package/dist/index.js +30 -69
- package/dist/init.js +112 -0
- package/package.json +3 -1
package/dist/cli.js
CHANGED
|
@@ -13786,6 +13786,134 @@ var require_dist = __commonJS((exports, module) => {
|
|
|
13786
13786
|
exports.default = formatsPlugin;
|
|
13787
13787
|
});
|
|
13788
13788
|
|
|
13789
|
+
// ../../node_modules/sisteransi/src/index.js
|
|
13790
|
+
var require_src = __commonJS((exports, module) => {
|
|
13791
|
+
var ESC = "\x1B";
|
|
13792
|
+
var CSI = `${ESC}[`;
|
|
13793
|
+
var beep = "\x07";
|
|
13794
|
+
var cursor = {
|
|
13795
|
+
to(x, y) {
|
|
13796
|
+
if (!y)
|
|
13797
|
+
return `${CSI}${x + 1}G`;
|
|
13798
|
+
return `${CSI}${y + 1};${x + 1}H`;
|
|
13799
|
+
},
|
|
13800
|
+
move(x, y) {
|
|
13801
|
+
let ret = "";
|
|
13802
|
+
if (x < 0)
|
|
13803
|
+
ret += `${CSI}${-x}D`;
|
|
13804
|
+
else if (x > 0)
|
|
13805
|
+
ret += `${CSI}${x}C`;
|
|
13806
|
+
if (y < 0)
|
|
13807
|
+
ret += `${CSI}${-y}A`;
|
|
13808
|
+
else if (y > 0)
|
|
13809
|
+
ret += `${CSI}${y}B`;
|
|
13810
|
+
return ret;
|
|
13811
|
+
},
|
|
13812
|
+
up: (count = 1) => `${CSI}${count}A`,
|
|
13813
|
+
down: (count = 1) => `${CSI}${count}B`,
|
|
13814
|
+
forward: (count = 1) => `${CSI}${count}C`,
|
|
13815
|
+
backward: (count = 1) => `${CSI}${count}D`,
|
|
13816
|
+
nextLine: (count = 1) => `${CSI}E`.repeat(count),
|
|
13817
|
+
prevLine: (count = 1) => `${CSI}F`.repeat(count),
|
|
13818
|
+
left: `${CSI}G`,
|
|
13819
|
+
hide: `${CSI}?25l`,
|
|
13820
|
+
show: `${CSI}?25h`,
|
|
13821
|
+
save: `${ESC}7`,
|
|
13822
|
+
restore: `${ESC}8`
|
|
13823
|
+
};
|
|
13824
|
+
var scroll = {
|
|
13825
|
+
up: (count = 1) => `${CSI}S`.repeat(count),
|
|
13826
|
+
down: (count = 1) => `${CSI}T`.repeat(count)
|
|
13827
|
+
};
|
|
13828
|
+
var erase = {
|
|
13829
|
+
screen: `${CSI}2J`,
|
|
13830
|
+
up: (count = 1) => `${CSI}1J`.repeat(count),
|
|
13831
|
+
down: (count = 1) => `${CSI}J`.repeat(count),
|
|
13832
|
+
line: `${CSI}2K`,
|
|
13833
|
+
lineEnd: `${CSI}K`,
|
|
13834
|
+
lineStart: `${CSI}1K`,
|
|
13835
|
+
lines(count) {
|
|
13836
|
+
let clear = "";
|
|
13837
|
+
for (let i = 0;i < count; i++)
|
|
13838
|
+
clear += this.line + (i < count - 1 ? cursor.up() : "");
|
|
13839
|
+
if (count)
|
|
13840
|
+
clear += cursor.left;
|
|
13841
|
+
return clear;
|
|
13842
|
+
}
|
|
13843
|
+
};
|
|
13844
|
+
module.exports = { cursor, scroll, erase, beep };
|
|
13845
|
+
});
|
|
13846
|
+
|
|
13847
|
+
// ../../node_modules/picocolors/picocolors.js
|
|
13848
|
+
var require_picocolors = __commonJS((exports, module) => {
|
|
13849
|
+
var p = process || {};
|
|
13850
|
+
var argv = p.argv || [];
|
|
13851
|
+
var env = p.env || {};
|
|
13852
|
+
var isColorSupported = !(!!env.NO_COLOR || argv.includes("--no-color")) && (!!env.FORCE_COLOR || argv.includes("--color") || p.platform === "win32" || (p.stdout || {}).isTTY && env.TERM !== "dumb" || !!env.CI);
|
|
13853
|
+
var formatter = (open, close, replace = open) => (input) => {
|
|
13854
|
+
let string4 = "" + input, index = string4.indexOf(close, open.length);
|
|
13855
|
+
return ~index ? open + replaceClose(string4, close, replace, index) + close : open + string4 + close;
|
|
13856
|
+
};
|
|
13857
|
+
var replaceClose = (string4, close, replace, index) => {
|
|
13858
|
+
let result = "", cursor = 0;
|
|
13859
|
+
do {
|
|
13860
|
+
result += string4.substring(cursor, index) + replace;
|
|
13861
|
+
cursor = index + close.length;
|
|
13862
|
+
index = string4.indexOf(close, cursor);
|
|
13863
|
+
} while (~index);
|
|
13864
|
+
return result + string4.substring(cursor);
|
|
13865
|
+
};
|
|
13866
|
+
var createColors = (enabled = isColorSupported) => {
|
|
13867
|
+
let f = enabled ? formatter : () => String;
|
|
13868
|
+
return {
|
|
13869
|
+
isColorSupported: enabled,
|
|
13870
|
+
reset: f("\x1B[0m", "\x1B[0m"),
|
|
13871
|
+
bold: f("\x1B[1m", "\x1B[22m", "\x1B[22m\x1B[1m"),
|
|
13872
|
+
dim: f("\x1B[2m", "\x1B[22m", "\x1B[22m\x1B[2m"),
|
|
13873
|
+
italic: f("\x1B[3m", "\x1B[23m"),
|
|
13874
|
+
underline: f("\x1B[4m", "\x1B[24m"),
|
|
13875
|
+
inverse: f("\x1B[7m", "\x1B[27m"),
|
|
13876
|
+
hidden: f("\x1B[8m", "\x1B[28m"),
|
|
13877
|
+
strikethrough: f("\x1B[9m", "\x1B[29m"),
|
|
13878
|
+
black: f("\x1B[30m", "\x1B[39m"),
|
|
13879
|
+
red: f("\x1B[31m", "\x1B[39m"),
|
|
13880
|
+
green: f("\x1B[32m", "\x1B[39m"),
|
|
13881
|
+
yellow: f("\x1B[33m", "\x1B[39m"),
|
|
13882
|
+
blue: f("\x1B[34m", "\x1B[39m"),
|
|
13883
|
+
magenta: f("\x1B[35m", "\x1B[39m"),
|
|
13884
|
+
cyan: f("\x1B[36m", "\x1B[39m"),
|
|
13885
|
+
white: f("\x1B[37m", "\x1B[39m"),
|
|
13886
|
+
gray: f("\x1B[90m", "\x1B[39m"),
|
|
13887
|
+
bgBlack: f("\x1B[40m", "\x1B[49m"),
|
|
13888
|
+
bgRed: f("\x1B[41m", "\x1B[49m"),
|
|
13889
|
+
bgGreen: f("\x1B[42m", "\x1B[49m"),
|
|
13890
|
+
bgYellow: f("\x1B[43m", "\x1B[49m"),
|
|
13891
|
+
bgBlue: f("\x1B[44m", "\x1B[49m"),
|
|
13892
|
+
bgMagenta: f("\x1B[45m", "\x1B[49m"),
|
|
13893
|
+
bgCyan: f("\x1B[46m", "\x1B[49m"),
|
|
13894
|
+
bgWhite: f("\x1B[47m", "\x1B[49m"),
|
|
13895
|
+
blackBright: f("\x1B[90m", "\x1B[39m"),
|
|
13896
|
+
redBright: f("\x1B[91m", "\x1B[39m"),
|
|
13897
|
+
greenBright: f("\x1B[92m", "\x1B[39m"),
|
|
13898
|
+
yellowBright: f("\x1B[93m", "\x1B[39m"),
|
|
13899
|
+
blueBright: f("\x1B[94m", "\x1B[39m"),
|
|
13900
|
+
magentaBright: f("\x1B[95m", "\x1B[39m"),
|
|
13901
|
+
cyanBright: f("\x1B[96m", "\x1B[39m"),
|
|
13902
|
+
whiteBright: f("\x1B[97m", "\x1B[39m"),
|
|
13903
|
+
bgBlackBright: f("\x1B[100m", "\x1B[49m"),
|
|
13904
|
+
bgRedBright: f("\x1B[101m", "\x1B[49m"),
|
|
13905
|
+
bgGreenBright: f("\x1B[102m", "\x1B[49m"),
|
|
13906
|
+
bgYellowBright: f("\x1B[103m", "\x1B[49m"),
|
|
13907
|
+
bgBlueBright: f("\x1B[104m", "\x1B[49m"),
|
|
13908
|
+
bgMagentaBright: f("\x1B[105m", "\x1B[49m"),
|
|
13909
|
+
bgCyanBright: f("\x1B[106m", "\x1B[49m"),
|
|
13910
|
+
bgWhiteBright: f("\x1B[107m", "\x1B[49m")
|
|
13911
|
+
};
|
|
13912
|
+
};
|
|
13913
|
+
module.exports = createColors();
|
|
13914
|
+
module.exports.createColors = createColors;
|
|
13915
|
+
});
|
|
13916
|
+
|
|
13789
13917
|
// src/init.ts
|
|
13790
13918
|
import { existsSync, mkdirSync, writeFileSync, readFileSync } from "node:fs";
|
|
13791
13919
|
import { join, dirname } from "node:path";
|
|
@@ -13865,6 +13993,94 @@ If pausing: \`harmony_end_agent_session\` with \`status: "paused"\`
|
|
|
13865
13993
|
|
|
13866
13994
|
**AI:** \`harmony_generate_prompt\`, \`harmony_process_command\`
|
|
13867
13995
|
`;
|
|
13996
|
+
var HARMONY_STANDUP_PROMPT = `# Harmony Daily Standup
|
|
13997
|
+
|
|
13998
|
+
Generate a daily standup summary for the current project.
|
|
13999
|
+
|
|
14000
|
+
## 1. Get Board State
|
|
14001
|
+
|
|
14002
|
+
Call \`harmony_get_board\` to get the full board state including:
|
|
14003
|
+
- All columns and their cards
|
|
14004
|
+
- Card priorities, assignees, and due dates
|
|
14005
|
+
- Active agent sessions
|
|
14006
|
+
|
|
14007
|
+
## 2. Analyze Board
|
|
14008
|
+
|
|
14009
|
+
Organize the information into standup categories:
|
|
14010
|
+
|
|
14011
|
+
### What was completed recently
|
|
14012
|
+
- Cards in "Done" or "Review" columns
|
|
14013
|
+
- Cards with recent activity (moved, updated)
|
|
14014
|
+
|
|
14015
|
+
### What's in progress
|
|
14016
|
+
- Cards in "In Progress" column
|
|
14017
|
+
- Cards with active agent sessions (show progress %)
|
|
14018
|
+
- Who's working on what
|
|
14019
|
+
|
|
14020
|
+
### What's blocked or at risk
|
|
14021
|
+
- High-priority cards not in progress
|
|
14022
|
+
- Overdue cards
|
|
14023
|
+
- Cards with blockers
|
|
14024
|
+
|
|
14025
|
+
### What's coming up
|
|
14026
|
+
- Cards in "To Do" column
|
|
14027
|
+
- Upcoming due dates
|
|
14028
|
+
|
|
14029
|
+
## 3. Present Summary
|
|
14030
|
+
|
|
14031
|
+
Format the summary as a clean, readable standup report:
|
|
14032
|
+
- Use bullet points for easy scanning
|
|
14033
|
+
- Highlight priorities and blockers
|
|
14034
|
+
- Include card short IDs for easy reference (e.g., #42)
|
|
14035
|
+
- Note any agent work in progress
|
|
14036
|
+
`;
|
|
14037
|
+
var HARMONY_CLEANUP_PROMPT = `# Harmony Board Cleanup
|
|
14038
|
+
|
|
14039
|
+
Analyze the board and suggest cleanup actions.
|
|
14040
|
+
|
|
14041
|
+
## 1. Get Board State
|
|
14042
|
+
|
|
14043
|
+
Call \`harmony_get_board\` to get the full board state.
|
|
14044
|
+
|
|
14045
|
+
## 2. Identify Issues
|
|
14046
|
+
|
|
14047
|
+
Look for:
|
|
14048
|
+
|
|
14049
|
+
### Stale cards
|
|
14050
|
+
- Cards in "In Progress" for too long without updates
|
|
14051
|
+
- Cards with past due dates
|
|
14052
|
+
- Cards with no recent activity
|
|
14053
|
+
|
|
14054
|
+
### Organizational issues
|
|
14055
|
+
- Cards missing priorities
|
|
14056
|
+
- Cards missing assignees in active columns
|
|
14057
|
+
- Empty descriptions on complex cards
|
|
14058
|
+
|
|
14059
|
+
### Potential duplicates
|
|
14060
|
+
- Cards with similar titles
|
|
14061
|
+
- Use \`harmony_search_cards\` if needed to find related cards
|
|
14062
|
+
|
|
14063
|
+
## 3. Suggest Actions
|
|
14064
|
+
|
|
14065
|
+
For each issue found, suggest a specific action:
|
|
14066
|
+
- Move stale cards back to backlog
|
|
14067
|
+
- Archive completed cards
|
|
14068
|
+
- Update missing information
|
|
14069
|
+
- Merge or link duplicates
|
|
14070
|
+
|
|
14071
|
+
Present suggestions as a prioritized list with:
|
|
14072
|
+
- Card reference (#ID)
|
|
14073
|
+
- Current state
|
|
14074
|
+
- Suggested action
|
|
14075
|
+
- Why it matters
|
|
14076
|
+
|
|
14077
|
+
## 4. Optional: Execute Cleanup
|
|
14078
|
+
|
|
14079
|
+
If the user approves, execute the suggested actions:
|
|
14080
|
+
- Use \`harmony_move_card\` to reorganize
|
|
14081
|
+
- Use \`harmony_update_card\` to add missing info
|
|
14082
|
+
- Use \`harmony_add_link_to_card\` to link related cards
|
|
14083
|
+
`;
|
|
13868
14084
|
function ensureDir(dirPath) {
|
|
13869
14085
|
if (!existsSync(dirPath)) {
|
|
13870
14086
|
mkdirSync(dirPath, { recursive: true });
|
|
@@ -13923,6 +14139,30 @@ ${HARMONY_WORKFLOW_PROMPT.replace("Your agent identifier", "claude-code").replac
|
|
|
13923
14139
|
result.filesCreated.push(commandPath);
|
|
13924
14140
|
if (skipped)
|
|
13925
14141
|
result.filesSkipped.push(commandPath);
|
|
14142
|
+
const standupContent = `---
|
|
14143
|
+
description: Generate a daily standup summary for the current Harmony project
|
|
14144
|
+
---
|
|
14145
|
+
|
|
14146
|
+
${HARMONY_STANDUP_PROMPT}
|
|
14147
|
+
`;
|
|
14148
|
+
const standupPath = join(cwd, ".claude", "commands", "hmy-standup.md");
|
|
14149
|
+
const standupResult = writeFileIfNotExists(standupPath, standupContent, force);
|
|
14150
|
+
if (standupResult.created)
|
|
14151
|
+
result.filesCreated.push(standupPath);
|
|
14152
|
+
if (standupResult.skipped)
|
|
14153
|
+
result.filesSkipped.push(standupPath);
|
|
14154
|
+
const cleanupContent = `---
|
|
14155
|
+
description: Analyze the Harmony board and suggest cleanup actions for stale cards
|
|
14156
|
+
---
|
|
14157
|
+
|
|
14158
|
+
${HARMONY_CLEANUP_PROMPT}
|
|
14159
|
+
`;
|
|
14160
|
+
const cleanupPath = join(cwd, ".claude", "commands", "hmy-cleanup.md");
|
|
14161
|
+
const cleanupResult = writeFileIfNotExists(cleanupPath, cleanupContent, force);
|
|
14162
|
+
if (cleanupResult.created)
|
|
14163
|
+
result.filesCreated.push(cleanupPath);
|
|
14164
|
+
if (cleanupResult.skipped)
|
|
14165
|
+
result.filesSkipped.push(cleanupPath);
|
|
13926
14166
|
const globalConfigPath = join(homedir(), ".claude", "settings.json");
|
|
13927
14167
|
const mcpConfig = {
|
|
13928
14168
|
mcpServers: {
|
|
@@ -14183,7 +14423,7 @@ var {
|
|
|
14183
14423
|
} = import__.default;
|
|
14184
14424
|
|
|
14185
14425
|
// src/cli.ts
|
|
14186
|
-
import { createInterface } from "node:readline";
|
|
14426
|
+
import { createInterface as createInterface2 } from "node:readline";
|
|
14187
14427
|
|
|
14188
14428
|
// ../../node_modules/zod/v4/core/core.js
|
|
14189
14429
|
var NEVER = Object.freeze({
|
|
@@ -25251,7 +25491,8 @@ function loadConfig() {
|
|
|
25251
25491
|
apiKey: null,
|
|
25252
25492
|
apiUrl: DEFAULT_API_URL,
|
|
25253
25493
|
activeWorkspaceId: null,
|
|
25254
|
-
activeProjectId: null
|
|
25494
|
+
activeProjectId: null,
|
|
25495
|
+
userEmail: null
|
|
25255
25496
|
};
|
|
25256
25497
|
}
|
|
25257
25498
|
try {
|
|
@@ -25261,14 +25502,16 @@ function loadConfig() {
|
|
|
25261
25502
|
apiKey: config2.apiKey || null,
|
|
25262
25503
|
apiUrl: config2.apiUrl || DEFAULT_API_URL,
|
|
25263
25504
|
activeWorkspaceId: config2.activeWorkspaceId || null,
|
|
25264
|
-
activeProjectId: config2.activeProjectId || null
|
|
25505
|
+
activeProjectId: config2.activeProjectId || null,
|
|
25506
|
+
userEmail: config2.userEmail || null
|
|
25265
25507
|
};
|
|
25266
25508
|
} catch {
|
|
25267
25509
|
return {
|
|
25268
25510
|
apiKey: null,
|
|
25269
25511
|
apiUrl: DEFAULT_API_URL,
|
|
25270
25512
|
activeWorkspaceId: null,
|
|
25271
|
-
activeProjectId: null
|
|
25513
|
+
activeProjectId: null,
|
|
25514
|
+
userEmail: null
|
|
25272
25515
|
};
|
|
25273
25516
|
}
|
|
25274
25517
|
}
|
|
@@ -25327,6 +25570,13 @@ function getApiUrl() {
|
|
|
25327
25570
|
const config2 = loadConfig();
|
|
25328
25571
|
return config2.apiUrl;
|
|
25329
25572
|
}
|
|
25573
|
+
function getUserEmail() {
|
|
25574
|
+
const config2 = loadConfig();
|
|
25575
|
+
return config2.userEmail;
|
|
25576
|
+
}
|
|
25577
|
+
function setUserEmail(email2) {
|
|
25578
|
+
saveConfig({ userEmail: email2 });
|
|
25579
|
+
}
|
|
25330
25580
|
function setActiveWorkspace(workspaceId, options) {
|
|
25331
25581
|
if (options?.local) {
|
|
25332
25582
|
saveLocalConfig({ workspaceId }, options.cwd);
|
|
@@ -26194,23 +26444,11 @@ var RESOURCES = [
|
|
|
26194
26444
|
mimeType: "application/json"
|
|
26195
26445
|
}
|
|
26196
26446
|
];
|
|
26197
|
-
var PROMPTS = {
|
|
26198
|
-
harmony_daily_standup: {
|
|
26199
|
-
name: "Daily Standup Summary",
|
|
26200
|
-
description: "Generate a summary of recent activity and current work items",
|
|
26201
|
-
arguments: [{ name: "projectId", description: "Project to summarize", required: false }]
|
|
26202
|
-
},
|
|
26203
|
-
harmony_board_cleanup: {
|
|
26204
|
-
name: "Board Cleanup Suggestions",
|
|
26205
|
-
description: "Identify stale cards and suggest cleanup actions",
|
|
26206
|
-
arguments: []
|
|
26207
|
-
}
|
|
26208
|
-
};
|
|
26209
26447
|
|
|
26210
26448
|
class HarmonyMCPServer {
|
|
26211
26449
|
server;
|
|
26212
26450
|
constructor() {
|
|
26213
|
-
this.server = new Server({ name: "harmony-mcp", version: "1.0.0" }, { capabilities: { tools: {}, resources: {}
|
|
26451
|
+
this.server = new Server({ name: "harmony-mcp", version: "1.0.0" }, { capabilities: { tools: {}, resources: {} } });
|
|
26214
26452
|
this.setupHandlers();
|
|
26215
26453
|
}
|
|
26216
26454
|
setupHandlers() {
|
|
@@ -26258,58 +26496,6 @@ class HarmonyMCPServer {
|
|
|
26258
26496
|
}
|
|
26259
26497
|
throw new Error(`Unknown resource: ${uri}`);
|
|
26260
26498
|
});
|
|
26261
|
-
this.server.setRequestHandler(ListPromptsRequestSchema, async () => ({
|
|
26262
|
-
prompts: Object.entries(PROMPTS).map(([name, prompt]) => ({
|
|
26263
|
-
name,
|
|
26264
|
-
description: prompt.description,
|
|
26265
|
-
arguments: prompt.arguments
|
|
26266
|
-
}))
|
|
26267
|
-
}));
|
|
26268
|
-
this.server.setRequestHandler(GetPromptRequestSchema, async (request) => {
|
|
26269
|
-
const { name, arguments: args } = request.params;
|
|
26270
|
-
if (name === "harmony_daily_standup") {
|
|
26271
|
-
const projectId = args?.projectId || getActiveProjectId();
|
|
26272
|
-
if (!projectId) {
|
|
26273
|
-
return {
|
|
26274
|
-
messages: [
|
|
26275
|
-
{
|
|
26276
|
-
role: "user",
|
|
26277
|
-
content: { type: "text", text: "No project context. Please set a project first using harmony_set_project_context." }
|
|
26278
|
-
}
|
|
26279
|
-
]
|
|
26280
|
-
};
|
|
26281
|
-
}
|
|
26282
|
-
try {
|
|
26283
|
-
const client2 = getClient();
|
|
26284
|
-
const board = await client2.getBoard(projectId);
|
|
26285
|
-
return {
|
|
26286
|
-
messages: [
|
|
26287
|
-
{
|
|
26288
|
-
role: "user",
|
|
26289
|
-
content: {
|
|
26290
|
-
type: "text",
|
|
26291
|
-
text: `Generate a daily standup summary for this Harmony project board:
|
|
26292
|
-
|
|
26293
|
-
${JSON.stringify(board, null, 2)}
|
|
26294
|
-
|
|
26295
|
-
Include: cards moved recently, current in-progress items, blocked or high-priority items, and upcoming due dates.`
|
|
26296
|
-
}
|
|
26297
|
-
}
|
|
26298
|
-
]
|
|
26299
|
-
};
|
|
26300
|
-
} catch (error2) {
|
|
26301
|
-
return {
|
|
26302
|
-
messages: [
|
|
26303
|
-
{
|
|
26304
|
-
role: "user",
|
|
26305
|
-
content: { type: "text", text: `Error: ${error2 instanceof Error ? error2.message : String(error2)}` }
|
|
26306
|
-
}
|
|
26307
|
-
]
|
|
26308
|
-
};
|
|
26309
|
-
}
|
|
26310
|
-
}
|
|
26311
|
-
throw new Error(`Unknown prompt: ${name}`);
|
|
26312
|
-
});
|
|
26313
26499
|
}
|
|
26314
26500
|
async handleToolCall(name, args) {
|
|
26315
26501
|
if (!isConfigured()) {
|
|
@@ -26521,6 +26707,21 @@ Include: cards moved recently, current in-progress items, blocked or high-priori
|
|
|
26521
26707
|
const cardId = exports_external.string().uuid().parse(args.cardId);
|
|
26522
26708
|
const agentIdentifier = exports_external.string().min(1).parse(args.agentIdentifier);
|
|
26523
26709
|
const agentName = exports_external.string().min(1).parse(args.agentName);
|
|
26710
|
+
let assignedTo = null;
|
|
26711
|
+
const userEmail = getUserEmail();
|
|
26712
|
+
if (userEmail) {
|
|
26713
|
+
try {
|
|
26714
|
+
const workspaceId = getActiveWorkspaceId();
|
|
26715
|
+
if (workspaceId) {
|
|
26716
|
+
const { members } = await client2.getWorkspaceMembers(workspaceId);
|
|
26717
|
+
const user = members.find((m) => m.email === userEmail);
|
|
26718
|
+
if (user) {
|
|
26719
|
+
await client2.updateCard(cardId, { assigneeId: user.id });
|
|
26720
|
+
assignedTo = user.email;
|
|
26721
|
+
}
|
|
26722
|
+
}
|
|
26723
|
+
} catch {}
|
|
26724
|
+
}
|
|
26524
26725
|
const result = await client2.startAgentSession(cardId, {
|
|
26525
26726
|
agentIdentifier,
|
|
26526
26727
|
agentName,
|
|
@@ -26528,7 +26729,7 @@ Include: cards moved recently, current in-progress items, blocked or high-priori
|
|
|
26528
26729
|
currentTask: args.currentTask,
|
|
26529
26730
|
estimatedMinutesRemaining: args.estimatedMinutesRemaining
|
|
26530
26731
|
});
|
|
26531
|
-
return { success: true, ...result };
|
|
26732
|
+
return { success: true, assignedTo, ...result };
|
|
26532
26733
|
}
|
|
26533
26734
|
case "harmony_update_agent_progress": {
|
|
26534
26735
|
const cardId = exports_external.string().uuid().parse(args.cardId);
|
|
@@ -26626,8 +26827,1353 @@ Include: cards moved recently, current in-progress items, blocked or high-priori
|
|
|
26626
26827
|
}
|
|
26627
26828
|
}
|
|
26628
26829
|
|
|
26830
|
+
// ../../node_modules/@clack/core/dist/index.mjs
|
|
26831
|
+
var import_sisteransi = __toESM(require_src(), 1);
|
|
26832
|
+
var import_picocolors = __toESM(require_picocolors(), 1);
|
|
26833
|
+
import { stdin as $, stdout as j } from "node:process";
|
|
26834
|
+
import * as f from "node:readline";
|
|
26835
|
+
import M from "node:readline";
|
|
26836
|
+
import { WriteStream as U } from "node:tty";
|
|
26837
|
+
function J({ onlyFirst: t = false } = {}) {
|
|
26838
|
+
const F = ["[\\u001B\\u009B][[\\]()#;?]*(?:(?:(?:(?:;[-a-zA-Z\\d\\/#&.:=?%@~_]+)*|[a-zA-Z\\d]+(?:;[-a-zA-Z\\d\\/#&.:=?%@~_]*)*)?(?:\\u0007|\\u001B\\u005C|\\u009C))", "(?:(?:\\d{1,4}(?:;\\d{0,4})*)?[\\dA-PR-TZcf-nq-uy=><~]))"].join("|");
|
|
26839
|
+
return new RegExp(F, t ? undefined : "g");
|
|
26840
|
+
}
|
|
26841
|
+
var Q = J();
|
|
26842
|
+
function T(t) {
|
|
26843
|
+
if (typeof t != "string")
|
|
26844
|
+
throw new TypeError(`Expected a \`string\`, got \`${typeof t}\``);
|
|
26845
|
+
return t.replace(Q, "");
|
|
26846
|
+
}
|
|
26847
|
+
function O(t) {
|
|
26848
|
+
return t && t.__esModule && Object.prototype.hasOwnProperty.call(t, "default") ? t.default : t;
|
|
26849
|
+
}
|
|
26850
|
+
var P = { exports: {} };
|
|
26851
|
+
(function(t) {
|
|
26852
|
+
var u = {};
|
|
26853
|
+
t.exports = u, u.eastAsianWidth = function(e) {
|
|
26854
|
+
var s = e.charCodeAt(0), i = e.length == 2 ? e.charCodeAt(1) : 0, D = s;
|
|
26855
|
+
return 55296 <= s && s <= 56319 && 56320 <= i && i <= 57343 && (s &= 1023, i &= 1023, D = s << 10 | i, D += 65536), D == 12288 || 65281 <= D && D <= 65376 || 65504 <= D && D <= 65510 ? "F" : D == 8361 || 65377 <= D && D <= 65470 || 65474 <= D && D <= 65479 || 65482 <= D && D <= 65487 || 65490 <= D && D <= 65495 || 65498 <= D && D <= 65500 || 65512 <= D && D <= 65518 ? "H" : 4352 <= D && D <= 4447 || 4515 <= D && D <= 4519 || 4602 <= D && D <= 4607 || 9001 <= D && D <= 9002 || 11904 <= D && D <= 11929 || 11931 <= D && D <= 12019 || 12032 <= D && D <= 12245 || 12272 <= D && D <= 12283 || 12289 <= D && D <= 12350 || 12353 <= D && D <= 12438 || 12441 <= D && D <= 12543 || 12549 <= D && D <= 12589 || 12593 <= D && D <= 12686 || 12688 <= D && D <= 12730 || 12736 <= D && D <= 12771 || 12784 <= D && D <= 12830 || 12832 <= D && D <= 12871 || 12880 <= D && D <= 13054 || 13056 <= D && D <= 19903 || 19968 <= D && D <= 42124 || 42128 <= D && D <= 42182 || 43360 <= D && D <= 43388 || 44032 <= D && D <= 55203 || 55216 <= D && D <= 55238 || 55243 <= D && D <= 55291 || 63744 <= D && D <= 64255 || 65040 <= D && D <= 65049 || 65072 <= D && D <= 65106 || 65108 <= D && D <= 65126 || 65128 <= D && D <= 65131 || 110592 <= D && D <= 110593 || 127488 <= D && D <= 127490 || 127504 <= D && D <= 127546 || 127552 <= D && D <= 127560 || 127568 <= D && D <= 127569 || 131072 <= D && D <= 194367 || 177984 <= D && D <= 196605 || 196608 <= D && D <= 262141 ? "W" : 32 <= D && D <= 126 || 162 <= D && D <= 163 || 165 <= D && D <= 166 || D == 172 || D == 175 || 10214 <= D && D <= 10221 || 10629 <= D && D <= 10630 ? "Na" : D == 161 || D == 164 || 167 <= D && D <= 168 || D == 170 || 173 <= D && D <= 174 || 176 <= D && D <= 180 || 182 <= D && D <= 186 || 188 <= D && D <= 191 || D == 198 || D == 208 || 215 <= D && D <= 216 || 222 <= D && D <= 225 || D == 230 || 232 <= D && D <= 234 || 236 <= D && D <= 237 || D == 240 || 242 <= D && D <= 243 || 247 <= D && D <= 250 || D == 252 || D == 254 || D == 257 || D == 273 || D == 275 || D == 283 || 294 <= D && D <= 295 || D == 299 || 305 <= D && D <= 307 || D == 312 || 319 <= D && D <= 322 || D == 324 || 328 <= D && D <= 331 || D == 333 || 338 <= D && D <= 339 || 358 <= D && D <= 359 || D == 363 || D == 462 || D == 464 || D == 466 || D == 468 || D == 470 || D == 472 || D == 474 || D == 476 || D == 593 || D == 609 || D == 708 || D == 711 || 713 <= D && D <= 715 || D == 717 || D == 720 || 728 <= D && D <= 731 || D == 733 || D == 735 || 768 <= D && D <= 879 || 913 <= D && D <= 929 || 931 <= D && D <= 937 || 945 <= D && D <= 961 || 963 <= D && D <= 969 || D == 1025 || 1040 <= D && D <= 1103 || D == 1105 || D == 8208 || 8211 <= D && D <= 8214 || 8216 <= D && D <= 8217 || 8220 <= D && D <= 8221 || 8224 <= D && D <= 8226 || 8228 <= D && D <= 8231 || D == 8240 || 8242 <= D && D <= 8243 || D == 8245 || D == 8251 || D == 8254 || D == 8308 || D == 8319 || 8321 <= D && D <= 8324 || D == 8364 || D == 8451 || D == 8453 || D == 8457 || D == 8467 || D == 8470 || 8481 <= D && D <= 8482 || D == 8486 || D == 8491 || 8531 <= D && D <= 8532 || 8539 <= D && D <= 8542 || 8544 <= D && D <= 8555 || 8560 <= D && D <= 8569 || D == 8585 || 8592 <= D && D <= 8601 || 8632 <= D && D <= 8633 || D == 8658 || D == 8660 || D == 8679 || D == 8704 || 8706 <= D && D <= 8707 || 8711 <= D && D <= 8712 || D == 8715 || D == 8719 || D == 8721 || D == 8725 || D == 8730 || 8733 <= D && D <= 8736 || D == 8739 || D == 8741 || 8743 <= D && D <= 8748 || D == 8750 || 8756 <= D && D <= 8759 || 8764 <= D && D <= 8765 || D == 8776 || D == 8780 || D == 8786 || 8800 <= D && D <= 8801 || 8804 <= D && D <= 8807 || 8810 <= D && D <= 8811 || 8814 <= D && D <= 8815 || 8834 <= D && D <= 8835 || 8838 <= D && D <= 8839 || D == 8853 || D == 8857 || D == 8869 || D == 8895 || D == 8978 || 9312 <= D && D <= 9449 || 9451 <= D && D <= 9547 || 9552 <= D && D <= 9587 || 9600 <= D && D <= 9615 || 9618 <= D && D <= 9621 || 9632 <= D && D <= 9633 || 9635 <= D && D <= 9641 || 9650 <= D && D <= 9651 || 9654 <= D && D <= 9655 || 9660 <= D && D <= 9661 || 9664 <= D && D <= 9665 || 9670 <= D && D <= 9672 || D == 9675 || 9678 <= D && D <= 9681 || 9698 <= D && D <= 9701 || D == 9711 || 9733 <= D && D <= 9734 || D == 9737 || 9742 <= D && D <= 9743 || 9748 <= D && D <= 9749 || D == 9756 || D == 9758 || D == 9792 || D == 9794 || 9824 <= D && D <= 9825 || 9827 <= D && D <= 9829 || 9831 <= D && D <= 9834 || 9836 <= D && D <= 9837 || D == 9839 || 9886 <= D && D <= 9887 || 9918 <= D && D <= 9919 || 9924 <= D && D <= 9933 || 9935 <= D && D <= 9953 || D == 9955 || 9960 <= D && D <= 9983 || D == 10045 || D == 10071 || 10102 <= D && D <= 10111 || 11093 <= D && D <= 11097 || 12872 <= D && D <= 12879 || 57344 <= D && D <= 63743 || 65024 <= D && D <= 65039 || D == 65533 || 127232 <= D && D <= 127242 || 127248 <= D && D <= 127277 || 127280 <= D && D <= 127337 || 127344 <= D && D <= 127386 || 917760 <= D && D <= 917999 || 983040 <= D && D <= 1048573 || 1048576 <= D && D <= 1114109 ? "A" : "N";
|
|
26856
|
+
}, u.characterLength = function(e) {
|
|
26857
|
+
var s = this.eastAsianWidth(e);
|
|
26858
|
+
return s == "F" || s == "W" || s == "A" ? 2 : 1;
|
|
26859
|
+
};
|
|
26860
|
+
function F(e) {
|
|
26861
|
+
return e.match(/[\uD800-\uDBFF][\uDC00-\uDFFF]|[^\uD800-\uDFFF]/g) || [];
|
|
26862
|
+
}
|
|
26863
|
+
u.length = function(e) {
|
|
26864
|
+
for (var s = F(e), i = 0, D = 0;D < s.length; D++)
|
|
26865
|
+
i = i + this.characterLength(s[D]);
|
|
26866
|
+
return i;
|
|
26867
|
+
}, u.slice = function(e, s, i) {
|
|
26868
|
+
textLen = u.length(e), s = s || 0, i = i || 1, s < 0 && (s = textLen + s), i < 0 && (i = textLen + i);
|
|
26869
|
+
for (var D = "", C = 0, o = F(e), E = 0;E < o.length; E++) {
|
|
26870
|
+
var a = o[E], n = u.length(a);
|
|
26871
|
+
if (C >= s - (n == 2 ? 1 : 0))
|
|
26872
|
+
if (C + n <= i)
|
|
26873
|
+
D += a;
|
|
26874
|
+
else
|
|
26875
|
+
break;
|
|
26876
|
+
C += n;
|
|
26877
|
+
}
|
|
26878
|
+
return D;
|
|
26879
|
+
};
|
|
26880
|
+
})(P);
|
|
26881
|
+
var X = P.exports;
|
|
26882
|
+
var DD = O(X);
|
|
26883
|
+
var uD = function() {
|
|
26884
|
+
return /\uD83C\uDFF4\uDB40\uDC67\uDB40\uDC62(?:\uDB40\uDC77\uDB40\uDC6C\uDB40\uDC73|\uDB40\uDC73\uDB40\uDC63\uDB40\uDC74|\uDB40\uDC65\uDB40\uDC6E\uDB40\uDC67)\uDB40\uDC7F|(?:\uD83E\uDDD1\uD83C\uDFFF\u200D\u2764\uFE0F\u200D(?:\uD83D\uDC8B\u200D)?\uD83E\uDDD1|\uD83D\uDC69\uD83C\uDFFF\u200D\uD83E\uDD1D\u200D(?:\uD83D[\uDC68\uDC69]))(?:\uD83C[\uDFFB-\uDFFE])|(?:\uD83E\uDDD1\uD83C\uDFFE\u200D\u2764\uFE0F\u200D(?:\uD83D\uDC8B\u200D)?\uD83E\uDDD1|\uD83D\uDC69\uD83C\uDFFE\u200D\uD83E\uDD1D\u200D(?:\uD83D[\uDC68\uDC69]))(?:\uD83C[\uDFFB-\uDFFD\uDFFF])|(?:\uD83E\uDDD1\uD83C\uDFFD\u200D\u2764\uFE0F\u200D(?:\uD83D\uDC8B\u200D)?\uD83E\uDDD1|\uD83D\uDC69\uD83C\uDFFD\u200D\uD83E\uDD1D\u200D(?:\uD83D[\uDC68\uDC69]))(?:\uD83C[\uDFFB\uDFFC\uDFFE\uDFFF])|(?:\uD83E\uDDD1\uD83C\uDFFC\u200D\u2764\uFE0F\u200D(?:\uD83D\uDC8B\u200D)?\uD83E\uDDD1|\uD83D\uDC69\uD83C\uDFFC\u200D\uD83E\uDD1D\u200D(?:\uD83D[\uDC68\uDC69]))(?:\uD83C[\uDFFB\uDFFD-\uDFFF])|(?:\uD83E\uDDD1\uD83C\uDFFB\u200D\u2764\uFE0F\u200D(?:\uD83D\uDC8B\u200D)?\uD83E\uDDD1|\uD83D\uDC69\uD83C\uDFFB\u200D\uD83E\uDD1D\u200D(?:\uD83D[\uDC68\uDC69]))(?:\uD83C[\uDFFC-\uDFFF])|\uD83D\uDC68(?:\uD83C\uDFFB(?:\u200D(?:\u2764\uFE0F\u200D(?:\uD83D\uDC8B\u200D\uD83D\uDC68(?:\uD83C[\uDFFB-\uDFFF])|\uD83D\uDC68(?:\uD83C[\uDFFB-\uDFFF]))|\uD83E\uDD1D\u200D\uD83D\uDC68(?:\uD83C[\uDFFC-\uDFFF])|[\u2695\u2696\u2708]\uFE0F|\uD83C[\uDF3E\uDF73\uDF7C\uDF93\uDFA4\uDFA8\uDFEB\uDFED]|\uD83D[\uDCBB\uDCBC\uDD27\uDD2C\uDE80\uDE92]|\uD83E[\uDDAF-\uDDB3\uDDBC\uDDBD]))?|(?:\uD83C[\uDFFC-\uDFFF])\u200D\u2764\uFE0F\u200D(?:\uD83D\uDC8B\u200D\uD83D\uDC68(?:\uD83C[\uDFFB-\uDFFF])|\uD83D\uDC68(?:\uD83C[\uDFFB-\uDFFF]))|\u200D(?:\u2764\uFE0F\u200D(?:\uD83D\uDC8B\u200D)?\uD83D\uDC68|(?:\uD83D[\uDC68\uDC69])\u200D(?:\uD83D\uDC66\u200D\uD83D\uDC66|\uD83D\uDC67\u200D(?:\uD83D[\uDC66\uDC67]))|\uD83D\uDC66\u200D\uD83D\uDC66|\uD83D\uDC67\u200D(?:\uD83D[\uDC66\uDC67])|\uD83C[\uDF3E\uDF73\uDF7C\uDF93\uDFA4\uDFA8\uDFEB\uDFED]|\uD83D[\uDCBB\uDCBC\uDD27\uDD2C\uDE80\uDE92]|\uD83E[\uDDAF-\uDDB3\uDDBC\uDDBD])|\uD83C\uDFFF\u200D(?:\uD83E\uDD1D\u200D\uD83D\uDC68(?:\uD83C[\uDFFB-\uDFFE])|\uD83C[\uDF3E\uDF73\uDF7C\uDF93\uDFA4\uDFA8\uDFEB\uDFED]|\uD83D[\uDCBB\uDCBC\uDD27\uDD2C\uDE80\uDE92]|\uD83E[\uDDAF-\uDDB3\uDDBC\uDDBD])|\uD83C\uDFFE\u200D(?:\uD83E\uDD1D\u200D\uD83D\uDC68(?:\uD83C[\uDFFB-\uDFFD\uDFFF])|\uD83C[\uDF3E\uDF73\uDF7C\uDF93\uDFA4\uDFA8\uDFEB\uDFED]|\uD83D[\uDCBB\uDCBC\uDD27\uDD2C\uDE80\uDE92]|\uD83E[\uDDAF-\uDDB3\uDDBC\uDDBD])|\uD83C\uDFFD\u200D(?:\uD83E\uDD1D\u200D\uD83D\uDC68(?:\uD83C[\uDFFB\uDFFC\uDFFE\uDFFF])|\uD83C[\uDF3E\uDF73\uDF7C\uDF93\uDFA4\uDFA8\uDFEB\uDFED]|\uD83D[\uDCBB\uDCBC\uDD27\uDD2C\uDE80\uDE92]|\uD83E[\uDDAF-\uDDB3\uDDBC\uDDBD])|\uD83C\uDFFC\u200D(?:\uD83E\uDD1D\u200D\uD83D\uDC68(?:\uD83C[\uDFFB\uDFFD-\uDFFF])|\uD83C[\uDF3E\uDF73\uDF7C\uDF93\uDFA4\uDFA8\uDFEB\uDFED]|\uD83D[\uDCBB\uDCBC\uDD27\uDD2C\uDE80\uDE92]|\uD83E[\uDDAF-\uDDB3\uDDBC\uDDBD])|(?:\uD83C\uDFFF\u200D[\u2695\u2696\u2708]|\uD83C\uDFFE\u200D[\u2695\u2696\u2708]|\uD83C\uDFFD\u200D[\u2695\u2696\u2708]|\uD83C\uDFFC\u200D[\u2695\u2696\u2708]|\u200D[\u2695\u2696\u2708])\uFE0F|\u200D(?:(?:\uD83D[\uDC68\uDC69])\u200D(?:\uD83D[\uDC66\uDC67])|\uD83D[\uDC66\uDC67])|\uD83C\uDFFF|\uD83C\uDFFE|\uD83C\uDFFD|\uD83C\uDFFC)?|(?:\uD83D\uDC69(?:\uD83C\uDFFB\u200D\u2764\uFE0F\u200D(?:\uD83D\uDC8B\u200D(?:\uD83D[\uDC68\uDC69])|\uD83D[\uDC68\uDC69])|(?:\uD83C[\uDFFC-\uDFFF])\u200D\u2764\uFE0F\u200D(?:\uD83D\uDC8B\u200D(?:\uD83D[\uDC68\uDC69])|\uD83D[\uDC68\uDC69]))|\uD83E\uDDD1(?:\uD83C[\uDFFB-\uDFFF])\u200D\uD83E\uDD1D\u200D\uD83E\uDDD1)(?:\uD83C[\uDFFB-\uDFFF])|\uD83D\uDC69\u200D\uD83D\uDC69\u200D(?:\uD83D\uDC66\u200D\uD83D\uDC66|\uD83D\uDC67\u200D(?:\uD83D[\uDC66\uDC67]))|\uD83D\uDC69(?:\u200D(?:\u2764\uFE0F\u200D(?:\uD83D\uDC8B\u200D(?:\uD83D[\uDC68\uDC69])|\uD83D[\uDC68\uDC69])|\uD83C[\uDF3E\uDF73\uDF7C\uDF93\uDFA4\uDFA8\uDFEB\uDFED]|\uD83D[\uDCBB\uDCBC\uDD27\uDD2C\uDE80\uDE92]|\uD83E[\uDDAF-\uDDB3\uDDBC\uDDBD])|\uD83C\uDFFF\u200D(?:\uD83C[\uDF3E\uDF73\uDF7C\uDF93\uDFA4\uDFA8\uDFEB\uDFED]|\uD83D[\uDCBB\uDCBC\uDD27\uDD2C\uDE80\uDE92]|\uD83E[\uDDAF-\uDDB3\uDDBC\uDDBD])|\uD83C\uDFFE\u200D(?:\uD83C[\uDF3E\uDF73\uDF7C\uDF93\uDFA4\uDFA8\uDFEB\uDFED]|\uD83D[\uDCBB\uDCBC\uDD27\uDD2C\uDE80\uDE92]|\uD83E[\uDDAF-\uDDB3\uDDBC\uDDBD])|\uD83C\uDFFD\u200D(?:\uD83C[\uDF3E\uDF73\uDF7C\uDF93\uDFA4\uDFA8\uDFEB\uDFED]|\uD83D[\uDCBB\uDCBC\uDD27\uDD2C\uDE80\uDE92]|\uD83E[\uDDAF-\uDDB3\uDDBC\uDDBD])|\uD83C\uDFFC\u200D(?:\uD83C[\uDF3E\uDF73\uDF7C\uDF93\uDFA4\uDFA8\uDFEB\uDFED]|\uD83D[\uDCBB\uDCBC\uDD27\uDD2C\uDE80\uDE92]|\uD83E[\uDDAF-\uDDB3\uDDBC\uDDBD])|\uD83C\uDFFB\u200D(?:\uD83C[\uDF3E\uDF73\uDF7C\uDF93\uDFA4\uDFA8\uDFEB\uDFED]|\uD83D[\uDCBB\uDCBC\uDD27\uDD2C\uDE80\uDE92]|\uD83E[\uDDAF-\uDDB3\uDDBC\uDDBD]))|\uD83E\uDDD1(?:\u200D(?:\uD83E\uDD1D\u200D\uD83E\uDDD1|\uD83C[\uDF3E\uDF73\uDF7C\uDF84\uDF93\uDFA4\uDFA8\uDFEB\uDFED]|\uD83D[\uDCBB\uDCBC\uDD27\uDD2C\uDE80\uDE92]|\uD83E[\uDDAF-\uDDB3\uDDBC\uDDBD])|\uD83C\uDFFF\u200D(?:\uD83C[\uDF3E\uDF73\uDF7C\uDF84\uDF93\uDFA4\uDFA8\uDFEB\uDFED]|\uD83D[\uDCBB\uDCBC\uDD27\uDD2C\uDE80\uDE92]|\uD83E[\uDDAF-\uDDB3\uDDBC\uDDBD])|\uD83C\uDFFE\u200D(?:\uD83C[\uDF3E\uDF73\uDF7C\uDF84\uDF93\uDFA4\uDFA8\uDFEB\uDFED]|\uD83D[\uDCBB\uDCBC\uDD27\uDD2C\uDE80\uDE92]|\uD83E[\uDDAF-\uDDB3\uDDBC\uDDBD])|\uD83C\uDFFD\u200D(?:\uD83C[\uDF3E\uDF73\uDF7C\uDF84\uDF93\uDFA4\uDFA8\uDFEB\uDFED]|\uD83D[\uDCBB\uDCBC\uDD27\uDD2C\uDE80\uDE92]|\uD83E[\uDDAF-\uDDB3\uDDBC\uDDBD])|\uD83C\uDFFC\u200D(?:\uD83C[\uDF3E\uDF73\uDF7C\uDF84\uDF93\uDFA4\uDFA8\uDFEB\uDFED]|\uD83D[\uDCBB\uDCBC\uDD27\uDD2C\uDE80\uDE92]|\uD83E[\uDDAF-\uDDB3\uDDBC\uDDBD])|\uD83C\uDFFB\u200D(?:\uD83C[\uDF3E\uDF73\uDF7C\uDF84\uDF93\uDFA4\uDFA8\uDFEB\uDFED]|\uD83D[\uDCBB\uDCBC\uDD27\uDD2C\uDE80\uDE92]|\uD83E[\uDDAF-\uDDB3\uDDBC\uDDBD]))|\uD83D\uDC69\u200D\uD83D\uDC66\u200D\uD83D\uDC66|\uD83D\uDC69\u200D\uD83D\uDC69\u200D(?:\uD83D[\uDC66\uDC67])|\uD83D\uDC69\u200D\uD83D\uDC67\u200D(?:\uD83D[\uDC66\uDC67])|(?:\uD83D\uDC41\uFE0F\u200D\uD83D\uDDE8|\uD83E\uDDD1(?:\uD83C\uDFFF\u200D[\u2695\u2696\u2708]|\uD83C\uDFFE\u200D[\u2695\u2696\u2708]|\uD83C\uDFFD\u200D[\u2695\u2696\u2708]|\uD83C\uDFFC\u200D[\u2695\u2696\u2708]|\uD83C\uDFFB\u200D[\u2695\u2696\u2708]|\u200D[\u2695\u2696\u2708])|\uD83D\uDC69(?:\uD83C\uDFFF\u200D[\u2695\u2696\u2708]|\uD83C\uDFFE\u200D[\u2695\u2696\u2708]|\uD83C\uDFFD\u200D[\u2695\u2696\u2708]|\uD83C\uDFFC\u200D[\u2695\u2696\u2708]|\uD83C\uDFFB\u200D[\u2695\u2696\u2708]|\u200D[\u2695\u2696\u2708])|\uD83D\uDE36\u200D\uD83C\uDF2B|\uD83C\uDFF3\uFE0F\u200D\u26A7|\uD83D\uDC3B\u200D\u2744|(?:(?:\uD83C[\uDFC3\uDFC4\uDFCA]|\uD83D[\uDC6E\uDC70\uDC71\uDC73\uDC77\uDC81\uDC82\uDC86\uDC87\uDE45-\uDE47\uDE4B\uDE4D\uDE4E\uDEA3\uDEB4-\uDEB6]|\uD83E[\uDD26\uDD35\uDD37-\uDD39\uDD3D\uDD3E\uDDB8\uDDB9\uDDCD-\uDDCF\uDDD4\uDDD6-\uDDDD])(?:\uD83C[\uDFFB-\uDFFF])|\uD83D\uDC6F|\uD83E[\uDD3C\uDDDE\uDDDF])\u200D[\u2640\u2642]|(?:\u26F9|\uD83C[\uDFCB\uDFCC]|\uD83D\uDD75)(?:\uFE0F|\uD83C[\uDFFB-\uDFFF])\u200D[\u2640\u2642]|\uD83C\uDFF4\u200D\u2620|(?:\uD83C[\uDFC3\uDFC4\uDFCA]|\uD83D[\uDC6E\uDC70\uDC71\uDC73\uDC77\uDC81\uDC82\uDC86\uDC87\uDE45-\uDE47\uDE4B\uDE4D\uDE4E\uDEA3\uDEB4-\uDEB6]|\uD83E[\uDD26\uDD35\uDD37-\uDD39\uDD3D\uDD3E\uDDB8\uDDB9\uDDCD-\uDDCF\uDDD4\uDDD6-\uDDDD])\u200D[\u2640\u2642]|[\xA9\xAE\u203C\u2049\u2122\u2139\u2194-\u2199\u21A9\u21AA\u2328\u23CF\u23ED-\u23EF\u23F1\u23F2\u23F8-\u23FA\u24C2\u25AA\u25AB\u25B6\u25C0\u25FB\u25FC\u2600-\u2604\u260E\u2611\u2618\u2620\u2622\u2623\u2626\u262A\u262E\u262F\u2638-\u263A\u2640\u2642\u265F\u2660\u2663\u2665\u2666\u2668\u267B\u267E\u2692\u2694-\u2697\u2699\u269B\u269C\u26A0\u26A7\u26B0\u26B1\u26C8\u26CF\u26D1\u26D3\u26E9\u26F0\u26F1\u26F4\u26F7\u26F8\u2702\u2708\u2709\u270F\u2712\u2714\u2716\u271D\u2721\u2733\u2734\u2744\u2747\u2763\u27A1\u2934\u2935\u2B05-\u2B07\u3030\u303D\u3297\u3299]|\uD83C[\uDD70\uDD71\uDD7E\uDD7F\uDE02\uDE37\uDF21\uDF24-\uDF2C\uDF36\uDF7D\uDF96\uDF97\uDF99-\uDF9B\uDF9E\uDF9F\uDFCD\uDFCE\uDFD4-\uDFDF\uDFF5\uDFF7]|\uD83D[\uDC3F\uDCFD\uDD49\uDD4A\uDD6F\uDD70\uDD73\uDD76-\uDD79\uDD87\uDD8A-\uDD8D\uDDA5\uDDA8\uDDB1\uDDB2\uDDBC\uDDC2-\uDDC4\uDDD1-\uDDD3\uDDDC-\uDDDE\uDDE1\uDDE3\uDDE8\uDDEF\uDDF3\uDDFA\uDECB\uDECD-\uDECF\uDEE0-\uDEE5\uDEE9\uDEF0\uDEF3])\uFE0F|\uD83C\uDFF3\uFE0F\u200D\uD83C\uDF08|\uD83D\uDC69\u200D\uD83D\uDC67|\uD83D\uDC69\u200D\uD83D\uDC66|\uD83D\uDE35\u200D\uD83D\uDCAB|\uD83D\uDE2E\u200D\uD83D\uDCA8|\uD83D\uDC15\u200D\uD83E\uDDBA|\uD83E\uDDD1(?:\uD83C\uDFFF|\uD83C\uDFFE|\uD83C\uDFFD|\uD83C\uDFFC|\uD83C\uDFFB)?|\uD83D\uDC69(?:\uD83C\uDFFF|\uD83C\uDFFE|\uD83C\uDFFD|\uD83C\uDFFC|\uD83C\uDFFB)?|\uD83C\uDDFD\uD83C\uDDF0|\uD83C\uDDF6\uD83C\uDDE6|\uD83C\uDDF4\uD83C\uDDF2|\uD83D\uDC08\u200D\u2B1B|\u2764\uFE0F\u200D(?:\uD83D\uDD25|\uD83E\uDE79)|\uD83D\uDC41\uFE0F|\uD83C\uDFF3\uFE0F|\uD83C\uDDFF(?:\uD83C[\uDDE6\uDDF2\uDDFC])|\uD83C\uDDFE(?:\uD83C[\uDDEA\uDDF9])|\uD83C\uDDFC(?:\uD83C[\uDDEB\uDDF8])|\uD83C\uDDFB(?:\uD83C[\uDDE6\uDDE8\uDDEA\uDDEC\uDDEE\uDDF3\uDDFA])|\uD83C\uDDFA(?:\uD83C[\uDDE6\uDDEC\uDDF2\uDDF3\uDDF8\uDDFE\uDDFF])|\uD83C\uDDF9(?:\uD83C[\uDDE6\uDDE8\uDDE9\uDDEB-\uDDED\uDDEF-\uDDF4\uDDF7\uDDF9\uDDFB\uDDFC\uDDFF])|\uD83C\uDDF8(?:\uD83C[\uDDE6-\uDDEA\uDDEC-\uDDF4\uDDF7-\uDDF9\uDDFB\uDDFD-\uDDFF])|\uD83C\uDDF7(?:\uD83C[\uDDEA\uDDF4\uDDF8\uDDFA\uDDFC])|\uD83C\uDDF5(?:\uD83C[\uDDE6\uDDEA-\uDDED\uDDF0-\uDDF3\uDDF7-\uDDF9\uDDFC\uDDFE])|\uD83C\uDDF3(?:\uD83C[\uDDE6\uDDE8\uDDEA-\uDDEC\uDDEE\uDDF1\uDDF4\uDDF5\uDDF7\uDDFA\uDDFF])|\uD83C\uDDF2(?:\uD83C[\uDDE6\uDDE8-\uDDED\uDDF0-\uDDFF])|\uD83C\uDDF1(?:\uD83C[\uDDE6-\uDDE8\uDDEE\uDDF0\uDDF7-\uDDFB\uDDFE])|\uD83C\uDDF0(?:\uD83C[\uDDEA\uDDEC-\uDDEE\uDDF2\uDDF3\uDDF5\uDDF7\uDDFC\uDDFE\uDDFF])|\uD83C\uDDEF(?:\uD83C[\uDDEA\uDDF2\uDDF4\uDDF5])|\uD83C\uDDEE(?:\uD83C[\uDDE8-\uDDEA\uDDF1-\uDDF4\uDDF6-\uDDF9])|\uD83C\uDDED(?:\uD83C[\uDDF0\uDDF2\uDDF3\uDDF7\uDDF9\uDDFA])|\uD83C\uDDEC(?:\uD83C[\uDDE6\uDDE7\uDDE9-\uDDEE\uDDF1-\uDDF3\uDDF5-\uDDFA\uDDFC\uDDFE])|\uD83C\uDDEB(?:\uD83C[\uDDEE-\uDDF0\uDDF2\uDDF4\uDDF7])|\uD83C\uDDEA(?:\uD83C[\uDDE6\uDDE8\uDDEA\uDDEC\uDDED\uDDF7-\uDDFA])|\uD83C\uDDE9(?:\uD83C[\uDDEA\uDDEC\uDDEF\uDDF0\uDDF2\uDDF4\uDDFF])|\uD83C\uDDE8(?:\uD83C[\uDDE6\uDDE8\uDDE9\uDDEB-\uDDEE\uDDF0-\uDDF5\uDDF7\uDDFA-\uDDFF])|\uD83C\uDDE7(?:\uD83C[\uDDE6\uDDE7\uDDE9-\uDDEF\uDDF1-\uDDF4\uDDF6-\uDDF9\uDDFB\uDDFC\uDDFE\uDDFF])|\uD83C\uDDE6(?:\uD83C[\uDDE8-\uDDEC\uDDEE\uDDF1\uDDF2\uDDF4\uDDF6-\uDDFA\uDDFC\uDDFD\uDDFF])|[#\*0-9]\uFE0F\u20E3|\u2764\uFE0F|(?:\uD83C[\uDFC3\uDFC4\uDFCA]|\uD83D[\uDC6E\uDC70\uDC71\uDC73\uDC77\uDC81\uDC82\uDC86\uDC87\uDE45-\uDE47\uDE4B\uDE4D\uDE4E\uDEA3\uDEB4-\uDEB6]|\uD83E[\uDD26\uDD35\uDD37-\uDD39\uDD3D\uDD3E\uDDB8\uDDB9\uDDCD-\uDDCF\uDDD4\uDDD6-\uDDDD])(?:\uD83C[\uDFFB-\uDFFF])|(?:\u26F9|\uD83C[\uDFCB\uDFCC]|\uD83D\uDD75)(?:\uFE0F|\uD83C[\uDFFB-\uDFFF])|\uD83C\uDFF4|(?:[\u270A\u270B]|\uD83C[\uDF85\uDFC2\uDFC7]|\uD83D[\uDC42\uDC43\uDC46-\uDC50\uDC66\uDC67\uDC6B-\uDC6D\uDC72\uDC74-\uDC76\uDC78\uDC7C\uDC83\uDC85\uDC8F\uDC91\uDCAA\uDD7A\uDD95\uDD96\uDE4C\uDE4F\uDEC0\uDECC]|\uD83E[\uDD0C\uDD0F\uDD18-\uDD1C\uDD1E\uDD1F\uDD30-\uDD34\uDD36\uDD77\uDDB5\uDDB6\uDDBB\uDDD2\uDDD3\uDDD5])(?:\uD83C[\uDFFB-\uDFFF])|(?:[\u261D\u270C\u270D]|\uD83D[\uDD74\uDD90])(?:\uFE0F|\uD83C[\uDFFB-\uDFFF])|[\u270A\u270B]|\uD83C[\uDF85\uDFC2\uDFC7]|\uD83D[\uDC08\uDC15\uDC3B\uDC42\uDC43\uDC46-\uDC50\uDC66\uDC67\uDC6B-\uDC6D\uDC72\uDC74-\uDC76\uDC78\uDC7C\uDC83\uDC85\uDC8F\uDC91\uDCAA\uDD7A\uDD95\uDD96\uDE2E\uDE35\uDE36\uDE4C\uDE4F\uDEC0\uDECC]|\uD83E[\uDD0C\uDD0F\uDD18-\uDD1C\uDD1E\uDD1F\uDD30-\uDD34\uDD36\uDD77\uDDB5\uDDB6\uDDBB\uDDD2\uDDD3\uDDD5]|\uD83C[\uDFC3\uDFC4\uDFCA]|\uD83D[\uDC6E\uDC70\uDC71\uDC73\uDC77\uDC81\uDC82\uDC86\uDC87\uDE45-\uDE47\uDE4B\uDE4D\uDE4E\uDEA3\uDEB4-\uDEB6]|\uD83E[\uDD26\uDD35\uDD37-\uDD39\uDD3D\uDD3E\uDDB8\uDDB9\uDDCD-\uDDCF\uDDD4\uDDD6-\uDDDD]|\uD83D\uDC6F|\uD83E[\uDD3C\uDDDE\uDDDF]|[\u231A\u231B\u23E9-\u23EC\u23F0\u23F3\u25FD\u25FE\u2614\u2615\u2648-\u2653\u267F\u2693\u26A1\u26AA\u26AB\u26BD\u26BE\u26C4\u26C5\u26CE\u26D4\u26EA\u26F2\u26F3\u26F5\u26FA\u26FD\u2705\u2728\u274C\u274E\u2753-\u2755\u2757\u2795-\u2797\u27B0\u27BF\u2B1B\u2B1C\u2B50\u2B55]|\uD83C[\uDC04\uDCCF\uDD8E\uDD91-\uDD9A\uDE01\uDE1A\uDE2F\uDE32-\uDE36\uDE38-\uDE3A\uDE50\uDE51\uDF00-\uDF20\uDF2D-\uDF35\uDF37-\uDF7C\uDF7E-\uDF84\uDF86-\uDF93\uDFA0-\uDFC1\uDFC5\uDFC6\uDFC8\uDFC9\uDFCF-\uDFD3\uDFE0-\uDFF0\uDFF8-\uDFFF]|\uD83D[\uDC00-\uDC07\uDC09-\uDC14\uDC16-\uDC3A\uDC3C-\uDC3E\uDC40\uDC44\uDC45\uDC51-\uDC65\uDC6A\uDC79-\uDC7B\uDC7D-\uDC80\uDC84\uDC88-\uDC8E\uDC90\uDC92-\uDCA9\uDCAB-\uDCFC\uDCFF-\uDD3D\uDD4B-\uDD4E\uDD50-\uDD67\uDDA4\uDDFB-\uDE2D\uDE2F-\uDE34\uDE37-\uDE44\uDE48-\uDE4A\uDE80-\uDEA2\uDEA4-\uDEB3\uDEB7-\uDEBF\uDEC1-\uDEC5\uDED0-\uDED2\uDED5-\uDED7\uDEEB\uDEEC\uDEF4-\uDEFC\uDFE0-\uDFEB]|\uD83E[\uDD0D\uDD0E\uDD10-\uDD17\uDD1D\uDD20-\uDD25\uDD27-\uDD2F\uDD3A\uDD3F-\uDD45\uDD47-\uDD76\uDD78\uDD7A-\uDDB4\uDDB7\uDDBA\uDDBC-\uDDCB\uDDD0\uDDE0-\uDDFF\uDE70-\uDE74\uDE78-\uDE7A\uDE80-\uDE86\uDE90-\uDEA8\uDEB0-\uDEB6\uDEC0-\uDEC2\uDED0-\uDED6]|(?:[\u231A\u231B\u23E9-\u23EC\u23F0\u23F3\u25FD\u25FE\u2614\u2615\u2648-\u2653\u267F\u2693\u26A1\u26AA\u26AB\u26BD\u26BE\u26C4\u26C5\u26CE\u26D4\u26EA\u26F2\u26F3\u26F5\u26FA\u26FD\u2705\u270A\u270B\u2728\u274C\u274E\u2753-\u2755\u2757\u2795-\u2797\u27B0\u27BF\u2B1B\u2B1C\u2B50\u2B55]|\uD83C[\uDC04\uDCCF\uDD8E\uDD91-\uDD9A\uDDE6-\uDDFF\uDE01\uDE1A\uDE2F\uDE32-\uDE36\uDE38-\uDE3A\uDE50\uDE51\uDF00-\uDF20\uDF2D-\uDF35\uDF37-\uDF7C\uDF7E-\uDF93\uDFA0-\uDFCA\uDFCF-\uDFD3\uDFE0-\uDFF0\uDFF4\uDFF8-\uDFFF]|\uD83D[\uDC00-\uDC3E\uDC40\uDC42-\uDCFC\uDCFF-\uDD3D\uDD4B-\uDD4E\uDD50-\uDD67\uDD7A\uDD95\uDD96\uDDA4\uDDFB-\uDE4F\uDE80-\uDEC5\uDECC\uDED0-\uDED2\uDED5-\uDED7\uDEEB\uDEEC\uDEF4-\uDEFC\uDFE0-\uDFEB]|\uD83E[\uDD0C-\uDD3A\uDD3C-\uDD45\uDD47-\uDD78\uDD7A-\uDDCB\uDDCD-\uDDFF\uDE70-\uDE74\uDE78-\uDE7A\uDE80-\uDE86\uDE90-\uDEA8\uDEB0-\uDEB6\uDEC0-\uDEC2\uDED0-\uDED6])|(?:[#\*0-9\xA9\xAE\u203C\u2049\u2122\u2139\u2194-\u2199\u21A9\u21AA\u231A\u231B\u2328\u23CF\u23E9-\u23F3\u23F8-\u23FA\u24C2\u25AA\u25AB\u25B6\u25C0\u25FB-\u25FE\u2600-\u2604\u260E\u2611\u2614\u2615\u2618\u261D\u2620\u2622\u2623\u2626\u262A\u262E\u262F\u2638-\u263A\u2640\u2642\u2648-\u2653\u265F\u2660\u2663\u2665\u2666\u2668\u267B\u267E\u267F\u2692-\u2697\u2699\u269B\u269C\u26A0\u26A1\u26A7\u26AA\u26AB\u26B0\u26B1\u26BD\u26BE\u26C4\u26C5\u26C8\u26CE\u26CF\u26D1\u26D3\u26D4\u26E9\u26EA\u26F0-\u26F5\u26F7-\u26FA\u26FD\u2702\u2705\u2708-\u270D\u270F\u2712\u2714\u2716\u271D\u2721\u2728\u2733\u2734\u2744\u2747\u274C\u274E\u2753-\u2755\u2757\u2763\u2764\u2795-\u2797\u27A1\u27B0\u27BF\u2934\u2935\u2B05-\u2B07\u2B1B\u2B1C\u2B50\u2B55\u3030\u303D\u3297\u3299]|\uD83C[\uDC04\uDCCF\uDD70\uDD71\uDD7E\uDD7F\uDD8E\uDD91-\uDD9A\uDDE6-\uDDFF\uDE01\uDE02\uDE1A\uDE2F\uDE32-\uDE3A\uDE50\uDE51\uDF00-\uDF21\uDF24-\uDF93\uDF96\uDF97\uDF99-\uDF9B\uDF9E-\uDFF0\uDFF3-\uDFF5\uDFF7-\uDFFF]|\uD83D[\uDC00-\uDCFD\uDCFF-\uDD3D\uDD49-\uDD4E\uDD50-\uDD67\uDD6F\uDD70\uDD73-\uDD7A\uDD87\uDD8A-\uDD8D\uDD90\uDD95\uDD96\uDDA4\uDDA5\uDDA8\uDDB1\uDDB2\uDDBC\uDDC2-\uDDC4\uDDD1-\uDDD3\uDDDC-\uDDDE\uDDE1\uDDE3\uDDE8\uDDEF\uDDF3\uDDFA-\uDE4F\uDE80-\uDEC5\uDECB-\uDED2\uDED5-\uDED7\uDEE0-\uDEE5\uDEE9\uDEEB\uDEEC\uDEF0\uDEF3-\uDEFC\uDFE0-\uDFEB]|\uD83E[\uDD0C-\uDD3A\uDD3C-\uDD45\uDD47-\uDD78\uDD7A-\uDDCB\uDDCD-\uDDFF\uDE70-\uDE74\uDE78-\uDE7A\uDE80-\uDE86\uDE90-\uDEA8\uDEB0-\uDEB6\uDEC0-\uDEC2\uDED0-\uDED6])\uFE0F|(?:[\u261D\u26F9\u270A-\u270D]|\uD83C[\uDF85\uDFC2-\uDFC4\uDFC7\uDFCA-\uDFCC]|\uD83D[\uDC42\uDC43\uDC46-\uDC50\uDC66-\uDC78\uDC7C\uDC81-\uDC83\uDC85-\uDC87\uDC8F\uDC91\uDCAA\uDD74\uDD75\uDD7A\uDD90\uDD95\uDD96\uDE45-\uDE47\uDE4B-\uDE4F\uDEA3\uDEB4-\uDEB6\uDEC0\uDECC]|\uD83E[\uDD0C\uDD0F\uDD18-\uDD1F\uDD26\uDD30-\uDD39\uDD3C-\uDD3E\uDD77\uDDB5\uDDB6\uDDB8\uDDB9\uDDBB\uDDCD-\uDDCF\uDDD1-\uDDDD])/g;
|
|
26885
|
+
};
|
|
26886
|
+
var FD = O(uD);
|
|
26887
|
+
function A(t, u = {}) {
|
|
26888
|
+
if (typeof t != "string" || t.length === 0 || (u = { ambiguousIsNarrow: true, ...u }, t = T(t), t.length === 0))
|
|
26889
|
+
return 0;
|
|
26890
|
+
t = t.replace(FD(), " ");
|
|
26891
|
+
const F = u.ambiguousIsNarrow ? 1 : 2;
|
|
26892
|
+
let e = 0;
|
|
26893
|
+
for (const s of t) {
|
|
26894
|
+
const i = s.codePointAt(0);
|
|
26895
|
+
if (i <= 31 || i >= 127 && i <= 159 || i >= 768 && i <= 879)
|
|
26896
|
+
continue;
|
|
26897
|
+
switch (DD.eastAsianWidth(s)) {
|
|
26898
|
+
case "F":
|
|
26899
|
+
case "W":
|
|
26900
|
+
e += 2;
|
|
26901
|
+
break;
|
|
26902
|
+
case "A":
|
|
26903
|
+
e += F;
|
|
26904
|
+
break;
|
|
26905
|
+
default:
|
|
26906
|
+
e += 1;
|
|
26907
|
+
}
|
|
26908
|
+
}
|
|
26909
|
+
return e;
|
|
26910
|
+
}
|
|
26911
|
+
var m = 10;
|
|
26912
|
+
var L = (t = 0) => (u) => `\x1B[${u + t}m`;
|
|
26913
|
+
var N = (t = 0) => (u) => `\x1B[${38 + t};5;${u}m`;
|
|
26914
|
+
var I = (t = 0) => (u, F, e) => `\x1B[${38 + t};2;${u};${F};${e}m`;
|
|
26915
|
+
var r = { modifier: { reset: [0, 0], bold: [1, 22], dim: [2, 22], italic: [3, 23], underline: [4, 24], overline: [53, 55], inverse: [7, 27], hidden: [8, 28], strikethrough: [9, 29] }, color: { black: [30, 39], red: [31, 39], green: [32, 39], yellow: [33, 39], blue: [34, 39], magenta: [35, 39], cyan: [36, 39], white: [37, 39], blackBright: [90, 39], gray: [90, 39], grey: [90, 39], redBright: [91, 39], greenBright: [92, 39], yellowBright: [93, 39], blueBright: [94, 39], magentaBright: [95, 39], cyanBright: [96, 39], whiteBright: [97, 39] }, bgColor: { bgBlack: [40, 49], bgRed: [41, 49], bgGreen: [42, 49], bgYellow: [43, 49], bgBlue: [44, 49], bgMagenta: [45, 49], bgCyan: [46, 49], bgWhite: [47, 49], bgBlackBright: [100, 49], bgGray: [100, 49], bgGrey: [100, 49], bgRedBright: [101, 49], bgGreenBright: [102, 49], bgYellowBright: [103, 49], bgBlueBright: [104, 49], bgMagentaBright: [105, 49], bgCyanBright: [106, 49], bgWhiteBright: [107, 49] } };
|
|
26916
|
+
Object.keys(r.modifier);
|
|
26917
|
+
var tD = Object.keys(r.color);
|
|
26918
|
+
var eD = Object.keys(r.bgColor);
|
|
26919
|
+
[...tD, ...eD];
|
|
26920
|
+
function sD() {
|
|
26921
|
+
const t = new Map;
|
|
26922
|
+
for (const [u, F] of Object.entries(r)) {
|
|
26923
|
+
for (const [e, s] of Object.entries(F))
|
|
26924
|
+
r[e] = { open: `\x1B[${s[0]}m`, close: `\x1B[${s[1]}m` }, F[e] = r[e], t.set(s[0], s[1]);
|
|
26925
|
+
Object.defineProperty(r, u, { value: F, enumerable: false });
|
|
26926
|
+
}
|
|
26927
|
+
return Object.defineProperty(r, "codes", { value: t, enumerable: false }), r.color.close = "\x1B[39m", r.bgColor.close = "\x1B[49m", r.color.ansi = L(), r.color.ansi256 = N(), r.color.ansi16m = I(), r.bgColor.ansi = L(m), r.bgColor.ansi256 = N(m), r.bgColor.ansi16m = I(m), Object.defineProperties(r, { rgbToAnsi256: { value: (u, F, e) => u === F && F === e ? u < 8 ? 16 : u > 248 ? 231 : Math.round((u - 8) / 247 * 24) + 232 : 16 + 36 * Math.round(u / 255 * 5) + 6 * Math.round(F / 255 * 5) + Math.round(e / 255 * 5), enumerable: false }, hexToRgb: { value: (u) => {
|
|
26928
|
+
const F = /[a-f\d]{6}|[a-f\d]{3}/i.exec(u.toString(16));
|
|
26929
|
+
if (!F)
|
|
26930
|
+
return [0, 0, 0];
|
|
26931
|
+
let [e] = F;
|
|
26932
|
+
e.length === 3 && (e = [...e].map((i) => i + i).join(""));
|
|
26933
|
+
const s = Number.parseInt(e, 16);
|
|
26934
|
+
return [s >> 16 & 255, s >> 8 & 255, s & 255];
|
|
26935
|
+
}, enumerable: false }, hexToAnsi256: { value: (u) => r.rgbToAnsi256(...r.hexToRgb(u)), enumerable: false }, ansi256ToAnsi: { value: (u) => {
|
|
26936
|
+
if (u < 8)
|
|
26937
|
+
return 30 + u;
|
|
26938
|
+
if (u < 16)
|
|
26939
|
+
return 90 + (u - 8);
|
|
26940
|
+
let F, e, s;
|
|
26941
|
+
if (u >= 232)
|
|
26942
|
+
F = ((u - 232) * 10 + 8) / 255, e = F, s = F;
|
|
26943
|
+
else {
|
|
26944
|
+
u -= 16;
|
|
26945
|
+
const C = u % 36;
|
|
26946
|
+
F = Math.floor(u / 36) / 5, e = Math.floor(C / 6) / 5, s = C % 6 / 5;
|
|
26947
|
+
}
|
|
26948
|
+
const i = Math.max(F, e, s) * 2;
|
|
26949
|
+
if (i === 0)
|
|
26950
|
+
return 30;
|
|
26951
|
+
let D = 30 + (Math.round(s) << 2 | Math.round(e) << 1 | Math.round(F));
|
|
26952
|
+
return i === 2 && (D += 60), D;
|
|
26953
|
+
}, enumerable: false }, rgbToAnsi: { value: (u, F, e) => r.ansi256ToAnsi(r.rgbToAnsi256(u, F, e)), enumerable: false }, hexToAnsi: { value: (u) => r.ansi256ToAnsi(r.hexToAnsi256(u)), enumerable: false } }), r;
|
|
26954
|
+
}
|
|
26955
|
+
var iD = sD();
|
|
26956
|
+
var v = new Set(["\x1B", ""]);
|
|
26957
|
+
var CD = 39;
|
|
26958
|
+
var w = "\x07";
|
|
26959
|
+
var W = "[";
|
|
26960
|
+
var rD = "]";
|
|
26961
|
+
var R = "m";
|
|
26962
|
+
var y = `${rD}8;;`;
|
|
26963
|
+
var V = (t) => `${v.values().next().value}${W}${t}${R}`;
|
|
26964
|
+
var z = (t) => `${v.values().next().value}${y}${t}${w}`;
|
|
26965
|
+
var ED = (t) => t.split(" ").map((u) => A(u));
|
|
26966
|
+
var _ = (t, u, F) => {
|
|
26967
|
+
const e = [...u];
|
|
26968
|
+
let s = false, i = false, D = A(T(t[t.length - 1]));
|
|
26969
|
+
for (const [C, o] of e.entries()) {
|
|
26970
|
+
const E = A(o);
|
|
26971
|
+
if (D + E <= F ? t[t.length - 1] += o : (t.push(o), D = 0), v.has(o) && (s = true, i = e.slice(C + 1).join("").startsWith(y)), s) {
|
|
26972
|
+
i ? o === w && (s = false, i = false) : o === R && (s = false);
|
|
26973
|
+
continue;
|
|
26974
|
+
}
|
|
26975
|
+
D += E, D === F && C < e.length - 1 && (t.push(""), D = 0);
|
|
26976
|
+
}
|
|
26977
|
+
!D && t[t.length - 1].length > 0 && t.length > 1 && (t[t.length - 2] += t.pop());
|
|
26978
|
+
};
|
|
26979
|
+
var nD = (t) => {
|
|
26980
|
+
const u = t.split(" ");
|
|
26981
|
+
let F = u.length;
|
|
26982
|
+
for (;F > 0 && !(A(u[F - 1]) > 0); )
|
|
26983
|
+
F--;
|
|
26984
|
+
return F === u.length ? t : u.slice(0, F).join(" ") + u.slice(F).join("");
|
|
26985
|
+
};
|
|
26986
|
+
var oD = (t, u, F = {}) => {
|
|
26987
|
+
if (F.trim !== false && t.trim() === "")
|
|
26988
|
+
return "";
|
|
26989
|
+
let e = "", s, i;
|
|
26990
|
+
const D = ED(t);
|
|
26991
|
+
let C = [""];
|
|
26992
|
+
for (const [E, a] of t.split(" ").entries()) {
|
|
26993
|
+
F.trim !== false && (C[C.length - 1] = C[C.length - 1].trimStart());
|
|
26994
|
+
let n = A(C[C.length - 1]);
|
|
26995
|
+
if (E !== 0 && (n >= u && (F.wordWrap === false || F.trim === false) && (C.push(""), n = 0), (n > 0 || F.trim === false) && (C[C.length - 1] += " ", n++)), F.hard && D[E] > u) {
|
|
26996
|
+
const B = u - n, p = 1 + Math.floor((D[E] - B - 1) / u);
|
|
26997
|
+
Math.floor((D[E] - 1) / u) < p && C.push(""), _(C, a, u);
|
|
26998
|
+
continue;
|
|
26999
|
+
}
|
|
27000
|
+
if (n + D[E] > u && n > 0 && D[E] > 0) {
|
|
27001
|
+
if (F.wordWrap === false && n < u) {
|
|
27002
|
+
_(C, a, u);
|
|
27003
|
+
continue;
|
|
27004
|
+
}
|
|
27005
|
+
C.push("");
|
|
27006
|
+
}
|
|
27007
|
+
if (n + D[E] > u && F.wordWrap === false) {
|
|
27008
|
+
_(C, a, u);
|
|
27009
|
+
continue;
|
|
27010
|
+
}
|
|
27011
|
+
C[C.length - 1] += a;
|
|
27012
|
+
}
|
|
27013
|
+
F.trim !== false && (C = C.map((E) => nD(E)));
|
|
27014
|
+
const o = [...C.join(`
|
|
27015
|
+
`)];
|
|
27016
|
+
for (const [E, a] of o.entries()) {
|
|
27017
|
+
if (e += a, v.has(a)) {
|
|
27018
|
+
const { groups: B } = new RegExp(`(?:\\${W}(?<code>\\d+)m|\\${y}(?<uri>.*)${w})`).exec(o.slice(E).join("")) || { groups: {} };
|
|
27019
|
+
if (B.code !== undefined) {
|
|
27020
|
+
const p = Number.parseFloat(B.code);
|
|
27021
|
+
s = p === CD ? undefined : p;
|
|
27022
|
+
} else
|
|
27023
|
+
B.uri !== undefined && (i = B.uri.length === 0 ? undefined : B.uri);
|
|
27024
|
+
}
|
|
27025
|
+
const n = iD.codes.get(Number(s));
|
|
27026
|
+
o[E + 1] === `
|
|
27027
|
+
` ? (i && (e += z("")), s && n && (e += V(n))) : a === `
|
|
27028
|
+
` && (s && n && (e += V(s)), i && (e += z(i)));
|
|
27029
|
+
}
|
|
27030
|
+
return e;
|
|
27031
|
+
};
|
|
27032
|
+
function G(t, u, F) {
|
|
27033
|
+
return String(t).normalize().replace(/\r\n/g, `
|
|
27034
|
+
`).split(`
|
|
27035
|
+
`).map((e) => oD(e, u, F)).join(`
|
|
27036
|
+
`);
|
|
27037
|
+
}
|
|
27038
|
+
var aD = ["up", "down", "left", "right", "space", "enter", "cancel"];
|
|
27039
|
+
var c = { actions: new Set(aD), aliases: new Map([["k", "up"], ["j", "down"], ["h", "left"], ["l", "right"], ["\x03", "cancel"], ["escape", "cancel"]]) };
|
|
27040
|
+
function k(t, u) {
|
|
27041
|
+
if (typeof t == "string")
|
|
27042
|
+
return c.aliases.get(t) === u;
|
|
27043
|
+
for (const F of t)
|
|
27044
|
+
if (F !== undefined && k(F, u))
|
|
27045
|
+
return true;
|
|
27046
|
+
return false;
|
|
27047
|
+
}
|
|
27048
|
+
function lD(t, u) {
|
|
27049
|
+
if (t === u)
|
|
27050
|
+
return;
|
|
27051
|
+
const F = t.split(`
|
|
27052
|
+
`), e = u.split(`
|
|
27053
|
+
`), s = [];
|
|
27054
|
+
for (let i = 0;i < Math.max(F.length, e.length); i++)
|
|
27055
|
+
F[i] !== e[i] && s.push(i);
|
|
27056
|
+
return s;
|
|
27057
|
+
}
|
|
27058
|
+
var xD = globalThis.process.platform.startsWith("win");
|
|
27059
|
+
var S = Symbol("clack:cancel");
|
|
27060
|
+
function BD(t) {
|
|
27061
|
+
return t === S;
|
|
27062
|
+
}
|
|
27063
|
+
function d(t, u) {
|
|
27064
|
+
const F = t;
|
|
27065
|
+
F.isTTY && F.setRawMode(u);
|
|
27066
|
+
}
|
|
27067
|
+
function cD({ input: t = $, output: u = j, overwrite: F = true, hideCursor: e = true } = {}) {
|
|
27068
|
+
const s = f.createInterface({ input: t, output: u, prompt: "", tabSize: 1 });
|
|
27069
|
+
f.emitKeypressEvents(t, s), t.isTTY && t.setRawMode(true);
|
|
27070
|
+
const i = (D, { name: C, sequence: o }) => {
|
|
27071
|
+
const E = String(D);
|
|
27072
|
+
if (k([E, C, o], "cancel")) {
|
|
27073
|
+
e && u.write(import_sisteransi.cursor.show), process.exit(0);
|
|
27074
|
+
return;
|
|
27075
|
+
}
|
|
27076
|
+
if (!F)
|
|
27077
|
+
return;
|
|
27078
|
+
const a = C === "return" ? 0 : -1, n = C === "return" ? -1 : 0;
|
|
27079
|
+
f.moveCursor(u, a, n, () => {
|
|
27080
|
+
f.clearLine(u, 1, () => {
|
|
27081
|
+
t.once("keypress", i);
|
|
27082
|
+
});
|
|
27083
|
+
});
|
|
27084
|
+
};
|
|
27085
|
+
return e && u.write(import_sisteransi.cursor.hide), t.once("keypress", i), () => {
|
|
27086
|
+
t.off("keypress", i), e && u.write(import_sisteransi.cursor.show), t.isTTY && !xD && t.setRawMode(false), s.terminal = false, s.close();
|
|
27087
|
+
};
|
|
27088
|
+
}
|
|
27089
|
+
var AD = Object.defineProperty;
|
|
27090
|
+
var pD = (t, u, F) => (u in t) ? AD(t, u, { enumerable: true, configurable: true, writable: true, value: F }) : t[u] = F;
|
|
27091
|
+
var h = (t, u, F) => (pD(t, typeof u != "symbol" ? u + "" : u, F), F);
|
|
27092
|
+
|
|
27093
|
+
class x {
|
|
27094
|
+
constructor(u, F = true) {
|
|
27095
|
+
h(this, "input"), h(this, "output"), h(this, "_abortSignal"), h(this, "rl"), h(this, "opts"), h(this, "_render"), h(this, "_track", false), h(this, "_prevFrame", ""), h(this, "_subscribers", new Map), h(this, "_cursor", 0), h(this, "state", "initial"), h(this, "error", ""), h(this, "value");
|
|
27096
|
+
const { input: e = $, output: s = j, render: i, signal: D, ...C } = u;
|
|
27097
|
+
this.opts = C, this.onKeypress = this.onKeypress.bind(this), this.close = this.close.bind(this), this.render = this.render.bind(this), this._render = i.bind(this), this._track = F, this._abortSignal = D, this.input = e, this.output = s;
|
|
27098
|
+
}
|
|
27099
|
+
unsubscribe() {
|
|
27100
|
+
this._subscribers.clear();
|
|
27101
|
+
}
|
|
27102
|
+
setSubscriber(u, F) {
|
|
27103
|
+
const e = this._subscribers.get(u) ?? [];
|
|
27104
|
+
e.push(F), this._subscribers.set(u, e);
|
|
27105
|
+
}
|
|
27106
|
+
on(u, F) {
|
|
27107
|
+
this.setSubscriber(u, { cb: F });
|
|
27108
|
+
}
|
|
27109
|
+
once(u, F) {
|
|
27110
|
+
this.setSubscriber(u, { cb: F, once: true });
|
|
27111
|
+
}
|
|
27112
|
+
emit(u, ...F) {
|
|
27113
|
+
const e = this._subscribers.get(u) ?? [], s = [];
|
|
27114
|
+
for (const i of e)
|
|
27115
|
+
i.cb(...F), i.once && s.push(() => e.splice(e.indexOf(i), 1));
|
|
27116
|
+
for (const i of s)
|
|
27117
|
+
i();
|
|
27118
|
+
}
|
|
27119
|
+
prompt() {
|
|
27120
|
+
return new Promise((u, F) => {
|
|
27121
|
+
if (this._abortSignal) {
|
|
27122
|
+
if (this._abortSignal.aborted)
|
|
27123
|
+
return this.state = "cancel", this.close(), u(S);
|
|
27124
|
+
this._abortSignal.addEventListener("abort", () => {
|
|
27125
|
+
this.state = "cancel", this.close();
|
|
27126
|
+
}, { once: true });
|
|
27127
|
+
}
|
|
27128
|
+
const e = new U(0);
|
|
27129
|
+
e._write = (s, i, D) => {
|
|
27130
|
+
this._track && (this.value = this.rl?.line.replace(/\t/g, ""), this._cursor = this.rl?.cursor ?? 0, this.emit("value", this.value)), D();
|
|
27131
|
+
}, this.input.pipe(e), this.rl = M.createInterface({ input: this.input, output: e, tabSize: 2, prompt: "", escapeCodeTimeout: 50 }), M.emitKeypressEvents(this.input, this.rl), this.rl.prompt(), this.opts.initialValue !== undefined && this._track && this.rl.write(this.opts.initialValue), this.input.on("keypress", this.onKeypress), d(this.input, true), this.output.on("resize", this.render), this.render(), this.once("submit", () => {
|
|
27132
|
+
this.output.write(import_sisteransi.cursor.show), this.output.off("resize", this.render), d(this.input, false), u(this.value);
|
|
27133
|
+
}), this.once("cancel", () => {
|
|
27134
|
+
this.output.write(import_sisteransi.cursor.show), this.output.off("resize", this.render), d(this.input, false), u(S);
|
|
27135
|
+
});
|
|
27136
|
+
});
|
|
27137
|
+
}
|
|
27138
|
+
onKeypress(u, F) {
|
|
27139
|
+
if (this.state === "error" && (this.state = "active"), F?.name && (!this._track && c.aliases.has(F.name) && this.emit("cursor", c.aliases.get(F.name)), c.actions.has(F.name) && this.emit("cursor", F.name)), u && (u.toLowerCase() === "y" || u.toLowerCase() === "n") && this.emit("confirm", u.toLowerCase() === "y"), u === "\t" && this.opts.placeholder && (this.value || (this.rl?.write(this.opts.placeholder), this.emit("value", this.opts.placeholder))), u && this.emit("key", u.toLowerCase()), F?.name === "return") {
|
|
27140
|
+
if (this.opts.validate) {
|
|
27141
|
+
const e = this.opts.validate(this.value);
|
|
27142
|
+
e && (this.error = e instanceof Error ? e.message : e, this.state = "error", this.rl?.write(this.value));
|
|
27143
|
+
}
|
|
27144
|
+
this.state !== "error" && (this.state = "submit");
|
|
27145
|
+
}
|
|
27146
|
+
k([u, F?.name, F?.sequence], "cancel") && (this.state = "cancel"), (this.state === "submit" || this.state === "cancel") && this.emit("finalize"), this.render(), (this.state === "submit" || this.state === "cancel") && this.close();
|
|
27147
|
+
}
|
|
27148
|
+
close() {
|
|
27149
|
+
this.input.unpipe(), this.input.removeListener("keypress", this.onKeypress), this.output.write(`
|
|
27150
|
+
`), d(this.input, false), this.rl?.close(), this.rl = undefined, this.emit(`${this.state}`, this.value), this.unsubscribe();
|
|
27151
|
+
}
|
|
27152
|
+
restoreCursor() {
|
|
27153
|
+
const u = G(this._prevFrame, process.stdout.columns, { hard: true }).split(`
|
|
27154
|
+
`).length - 1;
|
|
27155
|
+
this.output.write(import_sisteransi.cursor.move(-999, u * -1));
|
|
27156
|
+
}
|
|
27157
|
+
render() {
|
|
27158
|
+
const u = G(this._render(this) ?? "", process.stdout.columns, { hard: true });
|
|
27159
|
+
if (u !== this._prevFrame) {
|
|
27160
|
+
if (this.state === "initial")
|
|
27161
|
+
this.output.write(import_sisteransi.cursor.hide);
|
|
27162
|
+
else {
|
|
27163
|
+
const F = lD(this._prevFrame, u);
|
|
27164
|
+
if (this.restoreCursor(), F && F?.length === 1) {
|
|
27165
|
+
const e = F[0];
|
|
27166
|
+
this.output.write(import_sisteransi.cursor.move(0, e)), this.output.write(import_sisteransi.erase.lines(1));
|
|
27167
|
+
const s = u.split(`
|
|
27168
|
+
`);
|
|
27169
|
+
this.output.write(s[e]), this._prevFrame = u, this.output.write(import_sisteransi.cursor.move(0, s.length - e - 1));
|
|
27170
|
+
return;
|
|
27171
|
+
}
|
|
27172
|
+
if (F && F?.length > 1) {
|
|
27173
|
+
const e = F[0];
|
|
27174
|
+
this.output.write(import_sisteransi.cursor.move(0, e)), this.output.write(import_sisteransi.erase.down());
|
|
27175
|
+
const s = u.split(`
|
|
27176
|
+
`).slice(e);
|
|
27177
|
+
this.output.write(s.join(`
|
|
27178
|
+
`)), this._prevFrame = u;
|
|
27179
|
+
return;
|
|
27180
|
+
}
|
|
27181
|
+
this.output.write(import_sisteransi.erase.down());
|
|
27182
|
+
}
|
|
27183
|
+
this.output.write(u), this.state === "initial" && (this.state = "active"), this._prevFrame = u;
|
|
27184
|
+
}
|
|
27185
|
+
}
|
|
27186
|
+
}
|
|
27187
|
+
|
|
27188
|
+
class fD extends x {
|
|
27189
|
+
get cursor() {
|
|
27190
|
+
return this.value ? 0 : 1;
|
|
27191
|
+
}
|
|
27192
|
+
get _value() {
|
|
27193
|
+
return this.cursor === 0;
|
|
27194
|
+
}
|
|
27195
|
+
constructor(u) {
|
|
27196
|
+
super(u, false), this.value = !!u.initialValue, this.on("value", () => {
|
|
27197
|
+
this.value = this._value;
|
|
27198
|
+
}), this.on("confirm", (F) => {
|
|
27199
|
+
this.output.write(import_sisteransi.cursor.move(0, -1)), this.value = F, this.state = "submit", this.close();
|
|
27200
|
+
}), this.on("cursor", () => {
|
|
27201
|
+
this.value = !this.value;
|
|
27202
|
+
});
|
|
27203
|
+
}
|
|
27204
|
+
}
|
|
27205
|
+
var bD = Object.defineProperty;
|
|
27206
|
+
var mD = (t, u, F) => (u in t) ? bD(t, u, { enumerable: true, configurable: true, writable: true, value: F }) : t[u] = F;
|
|
27207
|
+
var Y = (t, u, F) => (mD(t, typeof u != "symbol" ? u + "" : u, F), F);
|
|
27208
|
+
var wD = class extends x {
|
|
27209
|
+
constructor(u) {
|
|
27210
|
+
super(u, false), Y(this, "options"), Y(this, "cursor", 0), this.options = u.options, this.value = [...u.initialValues ?? []], this.cursor = Math.max(this.options.findIndex(({ value: F }) => F === u.cursorAt), 0), this.on("key", (F) => {
|
|
27211
|
+
F === "a" && this.toggleAll();
|
|
27212
|
+
}), this.on("cursor", (F) => {
|
|
27213
|
+
switch (F) {
|
|
27214
|
+
case "left":
|
|
27215
|
+
case "up":
|
|
27216
|
+
this.cursor = this.cursor === 0 ? this.options.length - 1 : this.cursor - 1;
|
|
27217
|
+
break;
|
|
27218
|
+
case "down":
|
|
27219
|
+
case "right":
|
|
27220
|
+
this.cursor = this.cursor === this.options.length - 1 ? 0 : this.cursor + 1;
|
|
27221
|
+
break;
|
|
27222
|
+
case "space":
|
|
27223
|
+
this.toggleValue();
|
|
27224
|
+
break;
|
|
27225
|
+
}
|
|
27226
|
+
});
|
|
27227
|
+
}
|
|
27228
|
+
get _value() {
|
|
27229
|
+
return this.options[this.cursor].value;
|
|
27230
|
+
}
|
|
27231
|
+
toggleAll() {
|
|
27232
|
+
const u = this.value.length === this.options.length;
|
|
27233
|
+
this.value = u ? [] : this.options.map((F) => F.value);
|
|
27234
|
+
}
|
|
27235
|
+
toggleValue() {
|
|
27236
|
+
const u = this.value.includes(this._value);
|
|
27237
|
+
this.value = u ? this.value.filter((F) => F !== this._value) : [...this.value, this._value];
|
|
27238
|
+
}
|
|
27239
|
+
};
|
|
27240
|
+
class PD extends x {
|
|
27241
|
+
get valueWithCursor() {
|
|
27242
|
+
if (this.state === "submit")
|
|
27243
|
+
return this.value;
|
|
27244
|
+
if (this.cursor >= this.value.length)
|
|
27245
|
+
return `${this.value}█`;
|
|
27246
|
+
const u = this.value.slice(0, this.cursor), [F, ...e] = this.value.slice(this.cursor);
|
|
27247
|
+
return `${u}${import_picocolors.default.inverse(F)}${e.join("")}`;
|
|
27248
|
+
}
|
|
27249
|
+
get cursor() {
|
|
27250
|
+
return this._cursor;
|
|
27251
|
+
}
|
|
27252
|
+
constructor(u) {
|
|
27253
|
+
super(u), this.on("finalize", () => {
|
|
27254
|
+
this.value || (this.value = u.defaultValue);
|
|
27255
|
+
});
|
|
27256
|
+
}
|
|
27257
|
+
}
|
|
27258
|
+
|
|
27259
|
+
// ../../node_modules/@clack/prompts/dist/index.mjs
|
|
27260
|
+
var import_picocolors2 = __toESM(require_picocolors(), 1);
|
|
27261
|
+
var import_sisteransi2 = __toESM(require_src(), 1);
|
|
27262
|
+
import p from "node:process";
|
|
27263
|
+
function X2() {
|
|
27264
|
+
return p.platform !== "win32" ? p.env.TERM !== "linux" : !!p.env.CI || !!p.env.WT_SESSION || !!p.env.TERMINUS_SUBLIME || p.env.ConEmuTask === "{cmd::Cmder}" || p.env.TERM_PROGRAM === "Terminus-Sublime" || p.env.TERM_PROGRAM === "vscode" || p.env.TERM === "xterm-256color" || p.env.TERM === "alacritty" || p.env.TERMINAL_EMULATOR === "JetBrains-JediTerm";
|
|
27265
|
+
}
|
|
27266
|
+
var E = X2();
|
|
27267
|
+
var u = (s, n) => E ? s : n;
|
|
27268
|
+
var ee = u("◆", "*");
|
|
27269
|
+
var A2 = u("■", "x");
|
|
27270
|
+
var B = u("▲", "x");
|
|
27271
|
+
var S2 = u("◇", "o");
|
|
27272
|
+
var te = u("┌", "T");
|
|
27273
|
+
var a = u("│", "|");
|
|
27274
|
+
var m2 = u("└", "—");
|
|
27275
|
+
var j2 = u("●", ">");
|
|
27276
|
+
var R2 = u("○", " ");
|
|
27277
|
+
var V2 = u("◻", "[•]");
|
|
27278
|
+
var M2 = u("◼", "[+]");
|
|
27279
|
+
var G2 = u("◻", "[ ]");
|
|
27280
|
+
var se = u("▪", "•");
|
|
27281
|
+
var N2 = u("─", "-");
|
|
27282
|
+
var re = u("╮", "+");
|
|
27283
|
+
var ie = u("├", "+");
|
|
27284
|
+
var ne = u("╯", "+");
|
|
27285
|
+
var ae = u("●", "•");
|
|
27286
|
+
var oe = u("◆", "*");
|
|
27287
|
+
var ce = u("▲", "!");
|
|
27288
|
+
var le = u("■", "x");
|
|
27289
|
+
var y2 = (s) => {
|
|
27290
|
+
switch (s) {
|
|
27291
|
+
case "initial":
|
|
27292
|
+
case "active":
|
|
27293
|
+
return import_picocolors2.default.cyan(ee);
|
|
27294
|
+
case "cancel":
|
|
27295
|
+
return import_picocolors2.default.red(A2);
|
|
27296
|
+
case "error":
|
|
27297
|
+
return import_picocolors2.default.yellow(B);
|
|
27298
|
+
case "submit":
|
|
27299
|
+
return import_picocolors2.default.green(S2);
|
|
27300
|
+
}
|
|
27301
|
+
};
|
|
27302
|
+
var k2 = (s) => {
|
|
27303
|
+
const { cursor: n, options: t, style: i } = s, r2 = s.maxItems ?? Number.POSITIVE_INFINITY, c2 = Math.max(process.stdout.rows - 4, 0), o = Math.min(c2, Math.max(r2, 5));
|
|
27304
|
+
let l2 = 0;
|
|
27305
|
+
n >= l2 + o - 3 ? l2 = Math.max(Math.min(n - o + 3, t.length - o), 0) : n < l2 + 2 && (l2 = Math.max(n - 2, 0));
|
|
27306
|
+
const $2 = o < t.length && l2 > 0, d2 = o < t.length && l2 + o < t.length;
|
|
27307
|
+
return t.slice(l2, l2 + o).map((w2, b2, C) => {
|
|
27308
|
+
const I2 = b2 === 0 && $2, x2 = b2 === C.length - 1 && d2;
|
|
27309
|
+
return I2 || x2 ? import_picocolors2.default.dim("...") : i(w2, b2 + l2 === n);
|
|
27310
|
+
});
|
|
27311
|
+
};
|
|
27312
|
+
var ue = (s) => new PD({ validate: s.validate, placeholder: s.placeholder, defaultValue: s.defaultValue, initialValue: s.initialValue, render() {
|
|
27313
|
+
const n = `${import_picocolors2.default.gray(a)}
|
|
27314
|
+
${y2(this.state)} ${s.message}
|
|
27315
|
+
`, t = s.placeholder ? import_picocolors2.default.inverse(s.placeholder[0]) + import_picocolors2.default.dim(s.placeholder.slice(1)) : import_picocolors2.default.inverse(import_picocolors2.default.hidden("_")), i = this.value ? this.valueWithCursor : t;
|
|
27316
|
+
switch (this.state) {
|
|
27317
|
+
case "error":
|
|
27318
|
+
return `${n.trim()}
|
|
27319
|
+
${import_picocolors2.default.yellow(a)} ${i}
|
|
27320
|
+
${import_picocolors2.default.yellow(m2)} ${import_picocolors2.default.yellow(this.error)}
|
|
27321
|
+
`;
|
|
27322
|
+
case "submit":
|
|
27323
|
+
return `${n}${import_picocolors2.default.gray(a)} ${import_picocolors2.default.dim(this.value || s.placeholder)}`;
|
|
27324
|
+
case "cancel":
|
|
27325
|
+
return `${n}${import_picocolors2.default.gray(a)} ${import_picocolors2.default.strikethrough(import_picocolors2.default.dim(this.value ?? ""))}${this.value?.trim() ? `
|
|
27326
|
+
${import_picocolors2.default.gray(a)}` : ""}`;
|
|
27327
|
+
default:
|
|
27328
|
+
return `${n}${import_picocolors2.default.cyan(a)} ${i}
|
|
27329
|
+
${import_picocolors2.default.cyan(m2)}
|
|
27330
|
+
`;
|
|
27331
|
+
}
|
|
27332
|
+
} }).prompt();
|
|
27333
|
+
var me = (s) => {
|
|
27334
|
+
const n = s.active ?? "Yes", t = s.inactive ?? "No";
|
|
27335
|
+
return new fD({ active: n, inactive: t, initialValue: s.initialValue ?? true, render() {
|
|
27336
|
+
const i = `${import_picocolors2.default.gray(a)}
|
|
27337
|
+
${y2(this.state)} ${s.message}
|
|
27338
|
+
`, r2 = this.value ? n : t;
|
|
27339
|
+
switch (this.state) {
|
|
27340
|
+
case "submit":
|
|
27341
|
+
return `${i}${import_picocolors2.default.gray(a)} ${import_picocolors2.default.dim(r2)}`;
|
|
27342
|
+
case "cancel":
|
|
27343
|
+
return `${i}${import_picocolors2.default.gray(a)} ${import_picocolors2.default.strikethrough(import_picocolors2.default.dim(r2))}
|
|
27344
|
+
${import_picocolors2.default.gray(a)}`;
|
|
27345
|
+
default:
|
|
27346
|
+
return `${i}${import_picocolors2.default.cyan(a)} ${this.value ? `${import_picocolors2.default.green(j2)} ${n}` : `${import_picocolors2.default.dim(R2)} ${import_picocolors2.default.dim(n)}`} ${import_picocolors2.default.dim("/")} ${this.value ? `${import_picocolors2.default.dim(R2)} ${import_picocolors2.default.dim(t)}` : `${import_picocolors2.default.green(j2)} ${t}`}
|
|
27347
|
+
${import_picocolors2.default.cyan(m2)}
|
|
27348
|
+
`;
|
|
27349
|
+
}
|
|
27350
|
+
} }).prompt();
|
|
27351
|
+
};
|
|
27352
|
+
var pe = (s) => {
|
|
27353
|
+
const n = (t, i) => {
|
|
27354
|
+
const r2 = t.label ?? String(t.value);
|
|
27355
|
+
return i === "active" ? `${import_picocolors2.default.cyan(V2)} ${r2} ${t.hint ? import_picocolors2.default.dim(`(${t.hint})`) : ""}` : i === "selected" ? `${import_picocolors2.default.green(M2)} ${import_picocolors2.default.dim(r2)}` : i === "cancelled" ? `${import_picocolors2.default.strikethrough(import_picocolors2.default.dim(r2))}` : i === "active-selected" ? `${import_picocolors2.default.green(M2)} ${r2} ${t.hint ? import_picocolors2.default.dim(`(${t.hint})`) : ""}` : i === "submitted" ? `${import_picocolors2.default.dim(r2)}` : `${import_picocolors2.default.dim(G2)} ${import_picocolors2.default.dim(r2)}`;
|
|
27356
|
+
};
|
|
27357
|
+
return new wD({ options: s.options, initialValues: s.initialValues, required: s.required ?? true, cursorAt: s.cursorAt, validate(t) {
|
|
27358
|
+
if (this.required && t.length === 0)
|
|
27359
|
+
return `Please select at least one option.
|
|
27360
|
+
${import_picocolors2.default.reset(import_picocolors2.default.dim(`Press ${import_picocolors2.default.gray(import_picocolors2.default.bgWhite(import_picocolors2.default.inverse(" space ")))} to select, ${import_picocolors2.default.gray(import_picocolors2.default.bgWhite(import_picocolors2.default.inverse(" enter ")))} to submit`))}`;
|
|
27361
|
+
}, render() {
|
|
27362
|
+
const t = `${import_picocolors2.default.gray(a)}
|
|
27363
|
+
${y2(this.state)} ${s.message}
|
|
27364
|
+
`, i = (r2, c2) => {
|
|
27365
|
+
const o = this.value.includes(r2.value);
|
|
27366
|
+
return c2 && o ? n(r2, "active-selected") : o ? n(r2, "selected") : n(r2, c2 ? "active" : "inactive");
|
|
27367
|
+
};
|
|
27368
|
+
switch (this.state) {
|
|
27369
|
+
case "submit":
|
|
27370
|
+
return `${t}${import_picocolors2.default.gray(a)} ${this.options.filter(({ value: r2 }) => this.value.includes(r2)).map((r2) => n(r2, "submitted")).join(import_picocolors2.default.dim(", ")) || import_picocolors2.default.dim("none")}`;
|
|
27371
|
+
case "cancel": {
|
|
27372
|
+
const r2 = this.options.filter(({ value: c2 }) => this.value.includes(c2)).map((c2) => n(c2, "cancelled")).join(import_picocolors2.default.dim(", "));
|
|
27373
|
+
return `${t}${import_picocolors2.default.gray(a)} ${r2.trim() ? `${r2}
|
|
27374
|
+
${import_picocolors2.default.gray(a)}` : ""}`;
|
|
27375
|
+
}
|
|
27376
|
+
case "error": {
|
|
27377
|
+
const r2 = this.error.split(`
|
|
27378
|
+
`).map((c2, o) => o === 0 ? `${import_picocolors2.default.yellow(m2)} ${import_picocolors2.default.yellow(c2)}` : ` ${c2}`).join(`
|
|
27379
|
+
`);
|
|
27380
|
+
return `${t + import_picocolors2.default.yellow(a)} ${k2({ options: this.options, cursor: this.cursor, maxItems: s.maxItems, style: i }).join(`
|
|
27381
|
+
${import_picocolors2.default.yellow(a)} `)}
|
|
27382
|
+
${r2}
|
|
27383
|
+
`;
|
|
27384
|
+
}
|
|
27385
|
+
default:
|
|
27386
|
+
return `${t}${import_picocolors2.default.cyan(a)} ${k2({ options: this.options, cursor: this.cursor, maxItems: s.maxItems, style: i }).join(`
|
|
27387
|
+
${import_picocolors2.default.cyan(a)} `)}
|
|
27388
|
+
${import_picocolors2.default.cyan(m2)}
|
|
27389
|
+
`;
|
|
27390
|
+
}
|
|
27391
|
+
} }).prompt();
|
|
27392
|
+
};
|
|
27393
|
+
var ve = (s = "") => {
|
|
27394
|
+
process.stdout.write(`${import_picocolors2.default.gray(m2)} ${import_picocolors2.default.red(s)}
|
|
27395
|
+
|
|
27396
|
+
`);
|
|
27397
|
+
};
|
|
27398
|
+
var fe = (s = "") => {
|
|
27399
|
+
process.stdout.write(`${import_picocolors2.default.gray(a)}
|
|
27400
|
+
${import_picocolors2.default.gray(m2)} ${s}
|
|
27401
|
+
|
|
27402
|
+
`);
|
|
27403
|
+
};
|
|
27404
|
+
var v2 = { message: (s = "", { symbol: n = import_picocolors2.default.gray(a) } = {}) => {
|
|
27405
|
+
const t = [`${import_picocolors2.default.gray(a)}`];
|
|
27406
|
+
if (s) {
|
|
27407
|
+
const [i, ...r2] = s.split(`
|
|
27408
|
+
`);
|
|
27409
|
+
t.push(`${n} ${i}`, ...r2.map((c2) => `${import_picocolors2.default.gray(a)} ${c2}`));
|
|
27410
|
+
}
|
|
27411
|
+
process.stdout.write(`${t.join(`
|
|
27412
|
+
`)}
|
|
27413
|
+
`);
|
|
27414
|
+
}, info: (s) => {
|
|
27415
|
+
v2.message(s, { symbol: import_picocolors2.default.blue(ae) });
|
|
27416
|
+
}, success: (s) => {
|
|
27417
|
+
v2.message(s, { symbol: import_picocolors2.default.green(oe) });
|
|
27418
|
+
}, step: (s) => {
|
|
27419
|
+
v2.message(s, { symbol: import_picocolors2.default.green(S2) });
|
|
27420
|
+
}, warn: (s) => {
|
|
27421
|
+
v2.message(s, { symbol: import_picocolors2.default.yellow(ce) });
|
|
27422
|
+
}, warning: (s) => {
|
|
27423
|
+
v2.warn(s);
|
|
27424
|
+
}, error: (s) => {
|
|
27425
|
+
v2.message(s, { symbol: import_picocolors2.default.red(le) });
|
|
27426
|
+
} };
|
|
27427
|
+
var L2 = () => {
|
|
27428
|
+
const s = E ? ["◒", "◐", "◓", "◑"] : ["•", "o", "O", "0"], n = E ? 80 : 120, t = process.env.CI === "true";
|
|
27429
|
+
let i, r2, c2 = false, o = "", l2;
|
|
27430
|
+
const $2 = (h2) => {
|
|
27431
|
+
const g2 = h2 > 1 ? "Something went wrong" : "Canceled";
|
|
27432
|
+
c2 && P2(g2, h2);
|
|
27433
|
+
}, d2 = () => $2(2), w2 = () => $2(1), b2 = () => {
|
|
27434
|
+
process.on("uncaughtExceptionMonitor", d2), process.on("unhandledRejection", d2), process.on("SIGINT", w2), process.on("SIGTERM", w2), process.on("exit", $2);
|
|
27435
|
+
}, C = () => {
|
|
27436
|
+
process.removeListener("uncaughtExceptionMonitor", d2), process.removeListener("unhandledRejection", d2), process.removeListener("SIGINT", w2), process.removeListener("SIGTERM", w2), process.removeListener("exit", $2);
|
|
27437
|
+
}, I2 = () => {
|
|
27438
|
+
if (l2 === undefined)
|
|
27439
|
+
return;
|
|
27440
|
+
t && process.stdout.write(`
|
|
27441
|
+
`);
|
|
27442
|
+
const h2 = l2.split(`
|
|
27443
|
+
`);
|
|
27444
|
+
process.stdout.write(import_sisteransi2.cursor.move(-999, h2.length - 1)), process.stdout.write(import_sisteransi2.erase.down(h2.length));
|
|
27445
|
+
}, x2 = (h2) => h2.replace(/\.+$/, ""), O2 = (h2 = "") => {
|
|
27446
|
+
c2 = true, i = cD(), o = x2(h2), process.stdout.write(`${import_picocolors2.default.gray(a)}
|
|
27447
|
+
`);
|
|
27448
|
+
let g2 = 0, f2 = 0;
|
|
27449
|
+
b2(), r2 = setInterval(() => {
|
|
27450
|
+
if (t && o === l2)
|
|
27451
|
+
return;
|
|
27452
|
+
I2(), l2 = o;
|
|
27453
|
+
const W2 = import_picocolors2.default.magenta(s[g2]), _2 = t ? "..." : ".".repeat(Math.floor(f2)).slice(0, 3);
|
|
27454
|
+
process.stdout.write(`${W2} ${o}${_2}`), g2 = g2 + 1 < s.length ? g2 + 1 : 0, f2 = f2 < s.length ? f2 + 0.125 : 0;
|
|
27455
|
+
}, n);
|
|
27456
|
+
}, P2 = (h2 = "", g2 = 0) => {
|
|
27457
|
+
c2 = false, clearInterval(r2), I2();
|
|
27458
|
+
const f2 = g2 === 0 ? import_picocolors2.default.green(S2) : g2 === 1 ? import_picocolors2.default.red(A2) : import_picocolors2.default.red(B);
|
|
27459
|
+
o = x2(h2 ?? o), process.stdout.write(`${f2} ${o}
|
|
27460
|
+
`), C(), i();
|
|
27461
|
+
};
|
|
27462
|
+
return { start: O2, stop: P2, message: (h2 = "") => {
|
|
27463
|
+
o = x2(h2 ?? o);
|
|
27464
|
+
} };
|
|
27465
|
+
};
|
|
27466
|
+
|
|
27467
|
+
// src/tui/setup.ts
|
|
27468
|
+
import { homedir as homedir5 } from "node:os";
|
|
27469
|
+
import { join as join4 } from "node:path";
|
|
27470
|
+
|
|
27471
|
+
// src/tui/theme.ts
|
|
27472
|
+
var pc = __toESM(require_picocolors(), 1);
|
|
27473
|
+
var symbols = {
|
|
27474
|
+
harmony: "▲",
|
|
27475
|
+
check: "✓",
|
|
27476
|
+
cross: "✗",
|
|
27477
|
+
bullet: "•",
|
|
27478
|
+
arrow: "→",
|
|
27479
|
+
arrowRight: "▸",
|
|
27480
|
+
dot: "●",
|
|
27481
|
+
dotEmpty: "○",
|
|
27482
|
+
info: "ℹ",
|
|
27483
|
+
warning: "⚠",
|
|
27484
|
+
pointer: "❯"
|
|
27485
|
+
};
|
|
27486
|
+
var colors = {
|
|
27487
|
+
brand: (text) => pc.cyan(text),
|
|
27488
|
+
brandBold: (text) => pc.bold(pc.cyan(text)),
|
|
27489
|
+
success: (text) => pc.green(text),
|
|
27490
|
+
error: (text) => pc.red(text),
|
|
27491
|
+
warning: (text) => pc.yellow(text),
|
|
27492
|
+
info: (text) => pc.blue(text),
|
|
27493
|
+
dim: (text) => pc.dim(text),
|
|
27494
|
+
bold: (text) => pc.bold(text),
|
|
27495
|
+
muted: (text) => pc.gray(text),
|
|
27496
|
+
highlight: (text) => pc.cyan(text),
|
|
27497
|
+
link: (text) => pc.underline(pc.cyan(text))
|
|
27498
|
+
};
|
|
27499
|
+
var messages = {
|
|
27500
|
+
header: () => {
|
|
27501
|
+
return `
|
|
27502
|
+
${colors.brandBold(" HARMONY")}
|
|
27503
|
+
${colors.dim(" Project management for AI agents")}
|
|
27504
|
+
`;
|
|
27505
|
+
},
|
|
27506
|
+
done: (message) => {
|
|
27507
|
+
return `${colors.success(symbols.check)} ${message}`;
|
|
27508
|
+
},
|
|
27509
|
+
fail: (message) => {
|
|
27510
|
+
return `${colors.error(symbols.cross)} ${message}`;
|
|
27511
|
+
},
|
|
27512
|
+
skip: (message) => {
|
|
27513
|
+
return `${colors.dim("-")} ${colors.dim(message)}`;
|
|
27514
|
+
},
|
|
27515
|
+
step: (number4, total, message) => {
|
|
27516
|
+
return `${colors.dim(`[${number4}/${total}]`)} ${message}`;
|
|
27517
|
+
},
|
|
27518
|
+
fileCreated: (path) => {
|
|
27519
|
+
return ` ${colors.success(symbols.check)} ${colors.dim(path)}`;
|
|
27520
|
+
},
|
|
27521
|
+
fileSkipped: (path) => {
|
|
27522
|
+
return ` ${colors.dim(symbols.bullet)} ${colors.dim(path)} ${colors.dim("(exists)")}`;
|
|
27523
|
+
},
|
|
27524
|
+
fileError: (path, error2) => {
|
|
27525
|
+
return ` ${colors.error(symbols.cross)} ${path}: ${colors.error(error2)}`;
|
|
27526
|
+
}
|
|
27527
|
+
};
|
|
27528
|
+
function formatPath(path, homeDir) {
|
|
27529
|
+
if (path.startsWith(homeDir)) {
|
|
27530
|
+
return `~${path.slice(homeDir.length)}`;
|
|
27531
|
+
}
|
|
27532
|
+
return path;
|
|
27533
|
+
}
|
|
27534
|
+
|
|
27535
|
+
// src/tui/agents.ts
|
|
27536
|
+
import { existsSync as existsSync3 } from "node:fs";
|
|
27537
|
+
import { join as join3 } from "node:path";
|
|
27538
|
+
import { homedir as homedir3 } from "node:os";
|
|
27539
|
+
var AGENT_DEFINITIONS = [
|
|
27540
|
+
{
|
|
27541
|
+
id: "claude",
|
|
27542
|
+
name: "Claude Code",
|
|
27543
|
+
description: "Anthropic CLI agent",
|
|
27544
|
+
hint: "/hmy <card>",
|
|
27545
|
+
globalPaths: [join3(homedir3(), ".claude")],
|
|
27546
|
+
localPaths: [".claude"]
|
|
27547
|
+
},
|
|
27548
|
+
{
|
|
27549
|
+
id: "codex",
|
|
27550
|
+
name: "Codex",
|
|
27551
|
+
description: "OpenAI coding agent",
|
|
27552
|
+
hint: "/prompts:hmy <card>",
|
|
27553
|
+
globalPaths: [join3(homedir3(), ".codex")],
|
|
27554
|
+
localPaths: ["AGENTS.md"]
|
|
27555
|
+
},
|
|
27556
|
+
{
|
|
27557
|
+
id: "cursor",
|
|
27558
|
+
name: "Cursor",
|
|
27559
|
+
description: "AI-powered IDE",
|
|
27560
|
+
hint: "MCP tools available automatically",
|
|
27561
|
+
globalPaths: [],
|
|
27562
|
+
localPaths: [".cursor", ".cursorrules"]
|
|
27563
|
+
},
|
|
27564
|
+
{
|
|
27565
|
+
id: "windsurf",
|
|
27566
|
+
name: "Windsurf",
|
|
27567
|
+
description: "Codeium AI IDE",
|
|
27568
|
+
hint: "MCP tools available automatically",
|
|
27569
|
+
globalPaths: [join3(homedir3(), ".codeium", "windsurf")],
|
|
27570
|
+
localPaths: [".windsurf", ".windsurfrules"]
|
|
27571
|
+
}
|
|
27572
|
+
];
|
|
27573
|
+
function detectAgents2(cwd = process.cwd()) {
|
|
27574
|
+
return AGENT_DEFINITIONS.map((def) => {
|
|
27575
|
+
const globalPath = def.globalPaths.find((p2) => existsSync3(p2)) || null;
|
|
27576
|
+
const localPath = def.localPaths.find((p2) => existsSync3(join3(cwd, p2))) || null;
|
|
27577
|
+
return {
|
|
27578
|
+
id: def.id,
|
|
27579
|
+
name: def.name,
|
|
27580
|
+
detected: !!(globalPath || localPath),
|
|
27581
|
+
globalPath,
|
|
27582
|
+
localPath: localPath ? join3(cwd, localPath) : null,
|
|
27583
|
+
description: def.description,
|
|
27584
|
+
hint: def.hint
|
|
27585
|
+
};
|
|
27586
|
+
});
|
|
27587
|
+
}
|
|
27588
|
+
|
|
27589
|
+
// src/tui/writer.ts
|
|
27590
|
+
import { existsSync as existsSync4, mkdirSync as mkdirSync3, readFileSync as readFileSync3, writeFileSync as writeFileSync3 } from "node:fs";
|
|
27591
|
+
import { dirname as dirname2 } from "node:path";
|
|
27592
|
+
import { homedir as homedir4 } from "node:os";
|
|
27593
|
+
function ensureDir2(dirPath) {
|
|
27594
|
+
if (!existsSync4(dirPath)) {
|
|
27595
|
+
mkdirSync3(dirPath, { recursive: true, mode: 493 });
|
|
27596
|
+
}
|
|
27597
|
+
}
|
|
27598
|
+
function writeFile(filePath, content, options = {}) {
|
|
27599
|
+
const exists = existsSync4(filePath);
|
|
27600
|
+
if (exists && !options.force) {
|
|
27601
|
+
return { path: filePath, action: "skip" };
|
|
27602
|
+
}
|
|
27603
|
+
try {
|
|
27604
|
+
ensureDir2(dirname2(filePath));
|
|
27605
|
+
const mode = filePath.includes(".harmony-mcp") ? 384 : 420;
|
|
27606
|
+
writeFileSync3(filePath, content, { mode });
|
|
27607
|
+
return { path: filePath, action: exists ? "update" : "create" };
|
|
27608
|
+
} catch (error2) {
|
|
27609
|
+
return {
|
|
27610
|
+
path: filePath,
|
|
27611
|
+
action: "skip",
|
|
27612
|
+
error: error2 instanceof Error ? error2.message : String(error2)
|
|
27613
|
+
};
|
|
27614
|
+
}
|
|
27615
|
+
}
|
|
27616
|
+
function mergeJsonFile2(filePath, updates, options = {}) {
|
|
27617
|
+
const exists = existsSync4(filePath);
|
|
27618
|
+
if (!exists) {
|
|
27619
|
+
try {
|
|
27620
|
+
ensureDir2(dirname2(filePath));
|
|
27621
|
+
writeFileSync3(filePath, JSON.stringify(updates, null, 2), { mode: 420 });
|
|
27622
|
+
return { path: filePath, action: "create" };
|
|
27623
|
+
} catch (error2) {
|
|
27624
|
+
return {
|
|
27625
|
+
path: filePath,
|
|
27626
|
+
action: "skip",
|
|
27627
|
+
error: error2 instanceof Error ? error2.message : String(error2)
|
|
27628
|
+
};
|
|
27629
|
+
}
|
|
27630
|
+
}
|
|
27631
|
+
try {
|
|
27632
|
+
const existing = JSON.parse(readFileSync3(filePath, "utf-8"));
|
|
27633
|
+
if (updates.mcpServers && existing.mcpServers) {
|
|
27634
|
+
const existingServers = existing.mcpServers;
|
|
27635
|
+
const updateServers = updates.mcpServers;
|
|
27636
|
+
if (existingServers.harmony && !options.force) {
|
|
27637
|
+
return { path: filePath, action: "skip" };
|
|
27638
|
+
}
|
|
27639
|
+
existing.mcpServers = { ...existingServers, ...updateServers };
|
|
27640
|
+
} else {
|
|
27641
|
+
Object.assign(existing, updates);
|
|
27642
|
+
}
|
|
27643
|
+
writeFileSync3(filePath, JSON.stringify(existing, null, 2), { mode: 420 });
|
|
27644
|
+
return { path: filePath, action: "merge" };
|
|
27645
|
+
} catch {
|
|
27646
|
+
if (options.force) {
|
|
27647
|
+
try {
|
|
27648
|
+
writeFileSync3(filePath, JSON.stringify(updates, null, 2), { mode: 420 });
|
|
27649
|
+
return { path: filePath, action: "update" };
|
|
27650
|
+
} catch (error2) {
|
|
27651
|
+
return {
|
|
27652
|
+
path: filePath,
|
|
27653
|
+
action: "skip",
|
|
27654
|
+
error: error2 instanceof Error ? error2.message : String(error2)
|
|
27655
|
+
};
|
|
27656
|
+
}
|
|
27657
|
+
}
|
|
27658
|
+
return { path: filePath, action: "skip", error: "Could not parse existing file" };
|
|
27659
|
+
}
|
|
27660
|
+
}
|
|
27661
|
+
function appendToToml(filePath, section, content, options = {}) {
|
|
27662
|
+
const exists = existsSync4(filePath);
|
|
27663
|
+
if (!exists) {
|
|
27664
|
+
try {
|
|
27665
|
+
ensureDir2(dirname2(filePath));
|
|
27666
|
+
writeFileSync3(filePath, content, { mode: 420 });
|
|
27667
|
+
return { path: filePath, action: "create" };
|
|
27668
|
+
} catch (error2) {
|
|
27669
|
+
return {
|
|
27670
|
+
path: filePath,
|
|
27671
|
+
action: "skip",
|
|
27672
|
+
error: error2 instanceof Error ? error2.message : String(error2)
|
|
27673
|
+
};
|
|
27674
|
+
}
|
|
27675
|
+
}
|
|
27676
|
+
try {
|
|
27677
|
+
const existing = readFileSync3(filePath, "utf-8");
|
|
27678
|
+
if (existing.includes(section)) {
|
|
27679
|
+
if (options.force) {
|
|
27680
|
+
const updated = existing.replace(new RegExp(`\\[${section.replace(/[.*+?^${}()|[\]\\]/g, "\\$&")}\\][\\s\\S]*?(?=\\[|$)`), content.trim() + `
|
|
27681
|
+
|
|
27682
|
+
`);
|
|
27683
|
+
writeFileSync3(filePath, updated, { mode: 420 });
|
|
27684
|
+
return { path: filePath, action: "update" };
|
|
27685
|
+
}
|
|
27686
|
+
return { path: filePath, action: "skip" };
|
|
27687
|
+
}
|
|
27688
|
+
writeFileSync3(filePath, existing + `
|
|
27689
|
+
` + content, { mode: 420 });
|
|
27690
|
+
return { path: filePath, action: "merge" };
|
|
27691
|
+
} catch (error2) {
|
|
27692
|
+
return {
|
|
27693
|
+
path: filePath,
|
|
27694
|
+
action: "skip",
|
|
27695
|
+
error: error2 instanceof Error ? error2.message : String(error2)
|
|
27696
|
+
};
|
|
27697
|
+
}
|
|
27698
|
+
}
|
|
27699
|
+
async function writeFilesWithProgress(files, options = {}) {
|
|
27700
|
+
const results = [];
|
|
27701
|
+
const home = homedir4();
|
|
27702
|
+
const spinner = L2();
|
|
27703
|
+
spinner.start("Writing configuration files...");
|
|
27704
|
+
for (const file of files) {
|
|
27705
|
+
let result;
|
|
27706
|
+
if (file.type === "json") {
|
|
27707
|
+
const jsonContent = JSON.parse(file.content);
|
|
27708
|
+
result = mergeJsonFile2(file.path, jsonContent, options);
|
|
27709
|
+
} else if (file.type === "toml" && file.tomlSection) {
|
|
27710
|
+
result = appendToToml(file.path, file.tomlSection, file.content, options);
|
|
27711
|
+
} else {
|
|
27712
|
+
result = writeFile(file.path, file.content, options);
|
|
27713
|
+
}
|
|
27714
|
+
results.push(result);
|
|
27715
|
+
await new Promise((resolve) => setTimeout(resolve, 50));
|
|
27716
|
+
}
|
|
27717
|
+
spinner.stop("Files written");
|
|
27718
|
+
for (const result of results) {
|
|
27719
|
+
const displayPath = formatPath(result.path, home);
|
|
27720
|
+
if (result.error) {
|
|
27721
|
+
console.log(messages.fileError(displayPath, result.error));
|
|
27722
|
+
} else if (result.action === "skip") {
|
|
27723
|
+
console.log(messages.fileSkipped(displayPath));
|
|
27724
|
+
} else {
|
|
27725
|
+
const actionLabel = result.action === "merge" ? "updated" : "created";
|
|
27726
|
+
console.log(` ${colors.success("✓")} ${colors.dim(displayPath)} ${colors.dim(`(${actionLabel})`)}`);
|
|
27727
|
+
}
|
|
27728
|
+
}
|
|
27729
|
+
return results;
|
|
27730
|
+
}
|
|
27731
|
+
function getWriteSummary(files, options = {}) {
|
|
27732
|
+
const toCreate = [];
|
|
27733
|
+
const toUpdate = [];
|
|
27734
|
+
const toSkip = [];
|
|
27735
|
+
const home = homedir4();
|
|
27736
|
+
for (const file of files) {
|
|
27737
|
+
const displayPath = formatPath(file.path, home);
|
|
27738
|
+
const exists = existsSync4(file.path);
|
|
27739
|
+
if (exists && !options.force) {
|
|
27740
|
+
toSkip.push(displayPath);
|
|
27741
|
+
} else if (exists) {
|
|
27742
|
+
toUpdate.push(displayPath);
|
|
27743
|
+
} else {
|
|
27744
|
+
toCreate.push(displayPath);
|
|
27745
|
+
}
|
|
27746
|
+
}
|
|
27747
|
+
return { toCreate, toUpdate, toSkip };
|
|
27748
|
+
}
|
|
27749
|
+
|
|
27750
|
+
// src/tui/setup.ts
|
|
27751
|
+
var HARMONY_WORKFLOW_PROMPT2 = `# Harmony Card Workflow
|
|
27752
|
+
|
|
27753
|
+
Start work on a Harmony card. Card reference: $ARGUMENTS
|
|
27754
|
+
|
|
27755
|
+
## 1. Find & Fetch Card
|
|
27756
|
+
|
|
27757
|
+
Parse the reference and fetch the card:
|
|
27758
|
+
- \`#42\` or \`42\` → \`harmony_get_card_by_short_id\` with \`shortId: 42\`
|
|
27759
|
+
- UUID → \`harmony_get_card\` with \`cardId\`
|
|
27760
|
+
- Name/text → \`harmony_search_cards\` with \`query\`
|
|
27761
|
+
|
|
27762
|
+
## 2. Get Board State
|
|
27763
|
+
|
|
27764
|
+
Call \`harmony_get_board\` to get columns and labels. From the response:
|
|
27765
|
+
- Find the "In Progress" (or "Progress") column ID
|
|
27766
|
+
- Find the "agent" label ID
|
|
27767
|
+
|
|
27768
|
+
## 3. Setup Card for Work
|
|
27769
|
+
|
|
27770
|
+
Execute these in sequence:
|
|
27771
|
+
1. \`harmony_move_card\` → Move to "In Progress" column
|
|
27772
|
+
2. \`harmony_add_label_to_card\` → Add "agent" label
|
|
27773
|
+
3. \`harmony_start_agent_session\`:
|
|
27774
|
+
- \`cardId\`: Card UUID
|
|
27775
|
+
- \`agentIdentifier\`: Your agent identifier
|
|
27776
|
+
- \`agentName\`: Your agent name
|
|
27777
|
+
- \`currentTask\`: "Analyzing card requirements"
|
|
27778
|
+
|
|
27779
|
+
## 4. Generate Work Prompt
|
|
27780
|
+
|
|
27781
|
+
Call \`harmony_generate_prompt\` with:
|
|
27782
|
+
- \`cardId\` or \`shortId\` (+ \`projectId\` if using shortId)
|
|
27783
|
+
- \`variant\`: Select based on task:
|
|
27784
|
+
- \`"execute"\` (default) → Clear tasks, bug fixes, well-defined work
|
|
27785
|
+
- \`"analysis"\` → Complex features, unclear requirements
|
|
27786
|
+
- \`"draft"\` → Medium complexity, want feedback first
|
|
27787
|
+
|
|
27788
|
+
The generated prompt provides role framing, focus areas, subtasks, linked cards, and suggested outputs.
|
|
27789
|
+
|
|
27790
|
+
## 5. Display Card Summary
|
|
27791
|
+
|
|
27792
|
+
Show the user: Card title, short ID, role, priority, labels, due date, description, and subtasks.
|
|
27793
|
+
|
|
27794
|
+
## 6. Implement Solution
|
|
27795
|
+
|
|
27796
|
+
Work on the card following the generated prompt's guidance. Update progress at milestones:
|
|
27797
|
+
- \`harmony_update_agent_progress\` with \`progressPercent\` (0-100), \`currentTask\`, \`status\`, \`blockers\`
|
|
27798
|
+
|
|
27799
|
+
**Progress checkpoints:** 20% (exploration), 50% (implementation), 80% (testing), 100% (done)
|
|
27800
|
+
|
|
27801
|
+
## 7. Complete Work
|
|
27802
|
+
|
|
27803
|
+
When finished:
|
|
27804
|
+
1. \`harmony_end_agent_session\` with \`status: "completed"\`, \`progressPercent: 100\`
|
|
27805
|
+
2. \`harmony_move_card\` to "Review" column
|
|
27806
|
+
3. Summarize accomplishments
|
|
27807
|
+
|
|
27808
|
+
If pausing: \`harmony_end_agent_session\` with \`status: "paused"\`
|
|
27809
|
+
|
|
27810
|
+
## Key Tools Reference
|
|
27811
|
+
|
|
27812
|
+
**Cards:** \`harmony_get_card\`, \`harmony_get_card_by_short_id\`, \`harmony_search_cards\`, \`harmony_create_card\`, \`harmony_update_card\`, \`harmony_move_card\`, \`harmony_delete_card\`, \`harmony_assign_card\`
|
|
27813
|
+
|
|
27814
|
+
**Subtasks:** \`harmony_create_subtask\`, \`harmony_toggle_subtask\`, \`harmony_delete_subtask\`
|
|
27815
|
+
|
|
27816
|
+
**Labels:** \`harmony_add_label_to_card\`, \`harmony_remove_label_from_card\`, \`harmony_create_label\`
|
|
27817
|
+
|
|
27818
|
+
**Links:** \`harmony_add_link_to_card\`, \`harmony_remove_link_from_card\`, \`harmony_get_card_links\`
|
|
27819
|
+
|
|
27820
|
+
**Board:** \`harmony_get_board\`, \`harmony_list_projects\`, \`harmony_get_context\`, \`harmony_set_project_context\`
|
|
27821
|
+
|
|
27822
|
+
**Sessions:** \`harmony_start_agent_session\`, \`harmony_update_agent_progress\`, \`harmony_end_agent_session\`, \`harmony_get_agent_session\`
|
|
27823
|
+
|
|
27824
|
+
**AI:** \`harmony_generate_prompt\`, \`harmony_process_command\`
|
|
27825
|
+
`;
|
|
27826
|
+
async function validateApiKey(apiKey, apiUrl = "https://gethmy.com/api") {
|
|
27827
|
+
try {
|
|
27828
|
+
const response = await fetch(`${apiUrl}/v1/workspaces`, {
|
|
27829
|
+
method: "GET",
|
|
27830
|
+
headers: {
|
|
27831
|
+
"Content-Type": "application/json",
|
|
27832
|
+
"X-API-Key": apiKey
|
|
27833
|
+
}
|
|
27834
|
+
});
|
|
27835
|
+
if (!response.ok) {
|
|
27836
|
+
const data = await response.json().catch(() => ({}));
|
|
27837
|
+
return {
|
|
27838
|
+
valid: false,
|
|
27839
|
+
error: data.error || `API returned ${response.status}`
|
|
27840
|
+
};
|
|
27841
|
+
}
|
|
27842
|
+
const meResponse = await fetch(`${apiUrl}/v1/me`, {
|
|
27843
|
+
method: "GET",
|
|
27844
|
+
headers: {
|
|
27845
|
+
"Content-Type": "application/json",
|
|
27846
|
+
"X-API-Key": apiKey
|
|
27847
|
+
}
|
|
27848
|
+
});
|
|
27849
|
+
if (meResponse.ok) {
|
|
27850
|
+
const meData = await meResponse.json();
|
|
27851
|
+
return { valid: true, email: meData.user?.email };
|
|
27852
|
+
}
|
|
27853
|
+
return { valid: true };
|
|
27854
|
+
} catch (error2) {
|
|
27855
|
+
return {
|
|
27856
|
+
valid: false,
|
|
27857
|
+
error: error2 instanceof Error ? error2.message : "Connection failed"
|
|
27858
|
+
};
|
|
27859
|
+
}
|
|
27860
|
+
}
|
|
27861
|
+
function getAgentFiles(agentId, cwd) {
|
|
27862
|
+
const home = homedir5();
|
|
27863
|
+
const files = [];
|
|
27864
|
+
switch (agentId) {
|
|
27865
|
+
case "claude": {
|
|
27866
|
+
const commandContent = `---
|
|
27867
|
+
description: Start working on a Harmony card (moves to In Progress, adds agent label)
|
|
27868
|
+
argument-hint: <card-reference>
|
|
27869
|
+
---
|
|
27870
|
+
|
|
27871
|
+
${HARMONY_WORKFLOW_PROMPT2.replace("Your agent identifier", "claude-code").replace("Your agent name", "Claude Code")}
|
|
27872
|
+
`;
|
|
27873
|
+
files.push({
|
|
27874
|
+
path: join4(cwd, ".claude", "commands", "hmy.md"),
|
|
27875
|
+
content: commandContent,
|
|
27876
|
+
type: "text"
|
|
27877
|
+
});
|
|
27878
|
+
files.push({
|
|
27879
|
+
path: join4(home, ".claude", "settings.json"),
|
|
27880
|
+
content: JSON.stringify({
|
|
27881
|
+
mcpServers: {
|
|
27882
|
+
harmony: {
|
|
27883
|
+
command: "npx",
|
|
27884
|
+
args: ["-y", "harmony-mcp@latest", "serve"]
|
|
27885
|
+
}
|
|
27886
|
+
}
|
|
27887
|
+
}, null, 2),
|
|
27888
|
+
type: "json"
|
|
27889
|
+
});
|
|
27890
|
+
break;
|
|
27891
|
+
}
|
|
27892
|
+
case "codex": {
|
|
27893
|
+
const agentsContent = `# Harmony Integration
|
|
27894
|
+
|
|
27895
|
+
This project uses Harmony for task management. When working on tasks:
|
|
27896
|
+
|
|
27897
|
+
## Starting Work on a Card
|
|
27898
|
+
|
|
27899
|
+
When given a card reference (e.g., #42 or a card name), follow this workflow:
|
|
27900
|
+
|
|
27901
|
+
1. Use \`harmony_get_card_by_short_id\` or \`harmony_search_cards\` to find the card
|
|
27902
|
+
2. Move the card to "In Progress" using \`harmony_move_card\`
|
|
27903
|
+
3. Add the "agent" label using \`harmony_add_label_to_card\`
|
|
27904
|
+
4. Start a session with \`harmony_start_agent_session\` (agentIdentifier: "codex", agentName: "OpenAI Codex")
|
|
27905
|
+
5. Show the card details to the user
|
|
27906
|
+
6. Use \`harmony_generate_prompt\` to get guidance, then implement the solution
|
|
27907
|
+
7. Update progress periodically with \`harmony_update_agent_progress\`
|
|
27908
|
+
8. When done, call \`harmony_end_agent_session\` and move to "Review"
|
|
27909
|
+
|
|
27910
|
+
## Available Harmony Tools
|
|
27911
|
+
|
|
27912
|
+
- \`harmony_get_card\`, \`harmony_get_card_by_short_id\`, \`harmony_search_cards\` - Find cards
|
|
27913
|
+
- \`harmony_move_card\` - Move cards between columns
|
|
27914
|
+
- \`harmony_add_label_to_card\`, \`harmony_remove_label_from_card\` - Manage labels
|
|
27915
|
+
- \`harmony_start_agent_session\`, \`harmony_update_agent_progress\`, \`harmony_end_agent_session\` - Track work
|
|
27916
|
+
- \`harmony_get_board\` - Get board state
|
|
27917
|
+
- \`harmony_generate_prompt\` - Get role-based guidance and focus areas for the card
|
|
27918
|
+
`;
|
|
27919
|
+
files.push({
|
|
27920
|
+
path: join4(cwd, "AGENTS.md"),
|
|
27921
|
+
content: agentsContent,
|
|
27922
|
+
type: "text"
|
|
27923
|
+
});
|
|
27924
|
+
const promptContent = `---
|
|
27925
|
+
name: hmy
|
|
27926
|
+
description: Start working on a Harmony card
|
|
27927
|
+
arguments:
|
|
27928
|
+
- name: card
|
|
27929
|
+
description: Card reference (#42, UUID, or name)
|
|
27930
|
+
required: true
|
|
27931
|
+
---
|
|
27932
|
+
|
|
27933
|
+
${HARMONY_WORKFLOW_PROMPT2.replace("$ARGUMENTS", "{{card}}").replace("Your agent identifier", "codex").replace("Your agent name", "OpenAI Codex")}
|
|
27934
|
+
`;
|
|
27935
|
+
files.push({
|
|
27936
|
+
path: join4(home, ".codex", "prompts", "hmy.md"),
|
|
27937
|
+
content: promptContent,
|
|
27938
|
+
type: "text"
|
|
27939
|
+
});
|
|
27940
|
+
const tomlContent = `
|
|
27941
|
+
# Harmony MCP Server
|
|
27942
|
+
[mcp_servers.harmony]
|
|
27943
|
+
command = "npx"
|
|
27944
|
+
args = ["-y", "harmony-mcp@latest", "serve"]
|
|
27945
|
+
`;
|
|
27946
|
+
files.push({
|
|
27947
|
+
path: join4(home, ".codex", "config.toml"),
|
|
27948
|
+
content: tomlContent,
|
|
27949
|
+
type: "toml",
|
|
27950
|
+
tomlSection: "mcp_servers.harmony"
|
|
27951
|
+
});
|
|
27952
|
+
break;
|
|
27953
|
+
}
|
|
27954
|
+
case "cursor": {
|
|
27955
|
+
files.push({
|
|
27956
|
+
path: join4(cwd, ".cursor", "mcp.json"),
|
|
27957
|
+
content: JSON.stringify({
|
|
27958
|
+
mcpServers: {
|
|
27959
|
+
harmony: {
|
|
27960
|
+
command: "npx",
|
|
27961
|
+
args: ["-y", "harmony-mcp@latest", "serve"]
|
|
27962
|
+
}
|
|
27963
|
+
}
|
|
27964
|
+
}, null, 2),
|
|
27965
|
+
type: "json"
|
|
27966
|
+
});
|
|
27967
|
+
const ruleContent = `---
|
|
27968
|
+
description: Harmony card workflow rule
|
|
27969
|
+
globs:
|
|
27970
|
+
- "**/*"
|
|
27971
|
+
alwaysApply: false
|
|
27972
|
+
---
|
|
27973
|
+
|
|
27974
|
+
# Harmony Integration
|
|
27975
|
+
|
|
27976
|
+
When the user asks you to work on a Harmony card (references like #42, card names, or UUIDs):
|
|
27977
|
+
|
|
27978
|
+
${HARMONY_WORKFLOW_PROMPT2.replace("$ARGUMENTS", "the card reference").replace("Your agent identifier", "cursor").replace("Your agent name", "Cursor AI")}
|
|
27979
|
+
`;
|
|
27980
|
+
files.push({
|
|
27981
|
+
path: join4(cwd, ".cursor", "rules", "harmony.mdc"),
|
|
27982
|
+
content: ruleContent,
|
|
27983
|
+
type: "text"
|
|
27984
|
+
});
|
|
27985
|
+
break;
|
|
27986
|
+
}
|
|
27987
|
+
case "windsurf": {
|
|
27988
|
+
files.push({
|
|
27989
|
+
path: join4(home, ".codeium", "windsurf", "mcp_config.json"),
|
|
27990
|
+
content: JSON.stringify({
|
|
27991
|
+
mcpServers: {
|
|
27992
|
+
harmony: {
|
|
27993
|
+
command: "npx",
|
|
27994
|
+
args: ["-y", "harmony-mcp@latest", "serve"],
|
|
27995
|
+
disabled: false,
|
|
27996
|
+
alwaysAllow: []
|
|
27997
|
+
}
|
|
27998
|
+
}
|
|
27999
|
+
}, null, 2),
|
|
28000
|
+
type: "json"
|
|
28001
|
+
});
|
|
28002
|
+
const ruleContent = `---
|
|
28003
|
+
trigger: model_decision
|
|
28004
|
+
description: Activate when user asks to work on a Harmony card (references like #42, card names, or task management)
|
|
28005
|
+
---
|
|
28006
|
+
|
|
28007
|
+
# Harmony Card Workflow
|
|
28008
|
+
|
|
28009
|
+
When working on a Harmony card:
|
|
28010
|
+
|
|
28011
|
+
${HARMONY_WORKFLOW_PROMPT2.replace("$ARGUMENTS", "the card reference").replace("Your agent identifier", "windsurf").replace("Your agent name", "Windsurf AI")}
|
|
28012
|
+
`;
|
|
28013
|
+
files.push({
|
|
28014
|
+
path: join4(cwd, ".windsurf", "rules", "harmony.md"),
|
|
28015
|
+
content: ruleContent,
|
|
28016
|
+
type: "text"
|
|
28017
|
+
});
|
|
28018
|
+
break;
|
|
28019
|
+
}
|
|
28020
|
+
}
|
|
28021
|
+
return files;
|
|
28022
|
+
}
|
|
28023
|
+
async function runSetup(options = {}) {
|
|
28024
|
+
const cwd = process.cwd();
|
|
28025
|
+
const home = homedir5();
|
|
28026
|
+
console.clear();
|
|
28027
|
+
console.log(messages.header());
|
|
28028
|
+
const existingConfig = loadConfig();
|
|
28029
|
+
const alreadyConfigured = isConfigured();
|
|
28030
|
+
let apiKey = options.apiKey || existingConfig.apiKey;
|
|
28031
|
+
let userEmail;
|
|
28032
|
+
if (!apiKey || !apiKey.startsWith("hmy_")) {
|
|
28033
|
+
const keyInput = await ue({
|
|
28034
|
+
message: "Enter your Harmony API key",
|
|
28035
|
+
placeholder: "hmy_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx",
|
|
28036
|
+
validate: (value) => {
|
|
28037
|
+
if (!value)
|
|
28038
|
+
return "API key is required";
|
|
28039
|
+
if (!value.startsWith("hmy_"))
|
|
28040
|
+
return 'API key must start with "hmy_"';
|
|
28041
|
+
if (value.length < 20)
|
|
28042
|
+
return "API key is too short";
|
|
28043
|
+
return;
|
|
28044
|
+
}
|
|
28045
|
+
});
|
|
28046
|
+
if (BD(keyInput)) {
|
|
28047
|
+
ve("Setup cancelled");
|
|
28048
|
+
process.exit(0);
|
|
28049
|
+
}
|
|
28050
|
+
apiKey = keyInput;
|
|
28051
|
+
} else if (alreadyConfigured) {
|
|
28052
|
+
v2.info(`Using existing API key: ${apiKey.slice(0, 8)}...`);
|
|
28053
|
+
}
|
|
28054
|
+
const spinner = L2();
|
|
28055
|
+
spinner.start("Validating API key...");
|
|
28056
|
+
const validation = await validateApiKey(apiKey);
|
|
28057
|
+
if (!validation.valid) {
|
|
28058
|
+
spinner.stop(colors.error("API key validation failed"));
|
|
28059
|
+
v2.error(validation.error || "Could not connect to Harmony API");
|
|
28060
|
+
v2.info("Get an API key at: https://gethmy.com/settings/api-keys");
|
|
28061
|
+
process.exit(1);
|
|
28062
|
+
}
|
|
28063
|
+
userEmail = validation.email;
|
|
28064
|
+
spinner.stop(colors.success(userEmail ? `Connected as ${userEmail}` : "API key validated"));
|
|
28065
|
+
const detectedAgents = detectAgents2(cwd);
|
|
28066
|
+
const hasDetected = detectedAgents.some((a2) => a2.detected);
|
|
28067
|
+
let selectedAgents;
|
|
28068
|
+
if (options.agents && options.agents.length > 0) {
|
|
28069
|
+
selectedAgents = options.agents;
|
|
28070
|
+
} else {
|
|
28071
|
+
const agentOptions = detectedAgents.map((agent) => ({
|
|
28072
|
+
value: agent.id,
|
|
28073
|
+
label: agent.name,
|
|
28074
|
+
hint: agent.detected ? colors.success(`${agent.description} (detected)`) : colors.dim(`${agent.description}`)
|
|
28075
|
+
}));
|
|
28076
|
+
const agentSelection = await pe({
|
|
28077
|
+
message: "Select agents to configure",
|
|
28078
|
+
options: agentOptions,
|
|
28079
|
+
initialValues: detectedAgents.filter((a2) => a2.detected).map((a2) => a2.id),
|
|
28080
|
+
required: true
|
|
28081
|
+
});
|
|
28082
|
+
if (BD(agentSelection)) {
|
|
28083
|
+
ve("Setup cancelled");
|
|
28084
|
+
process.exit(0);
|
|
28085
|
+
}
|
|
28086
|
+
selectedAgents = agentSelection;
|
|
28087
|
+
}
|
|
28088
|
+
if (selectedAgents.length === 0) {
|
|
28089
|
+
v2.warning("No agents selected. Exiting.");
|
|
28090
|
+
process.exit(0);
|
|
28091
|
+
}
|
|
28092
|
+
const allFiles = [];
|
|
28093
|
+
allFiles.push({
|
|
28094
|
+
path: getConfigPath(),
|
|
28095
|
+
content: JSON.stringify({
|
|
28096
|
+
apiKey,
|
|
28097
|
+
apiUrl: "https://gethmy.com/api",
|
|
28098
|
+
userEmail: userEmail || null,
|
|
28099
|
+
activeWorkspaceId: null,
|
|
28100
|
+
activeProjectId: null
|
|
28101
|
+
}, null, 2),
|
|
28102
|
+
type: "text"
|
|
28103
|
+
});
|
|
28104
|
+
for (const agentId of selectedAgents) {
|
|
28105
|
+
const agentFiles = getAgentFiles(agentId, cwd);
|
|
28106
|
+
allFiles.push(...agentFiles);
|
|
28107
|
+
}
|
|
28108
|
+
const summary = getWriteSummary(allFiles, { force: options.force });
|
|
28109
|
+
console.log("");
|
|
28110
|
+
v2.step("Summary");
|
|
28111
|
+
console.log("");
|
|
28112
|
+
console.log(` ${colors.bold("Config:")} ${formatPath(getConfigPath(), home)}`);
|
|
28113
|
+
console.log(` ${colors.bold("Agents:")} ${selectedAgents.map((a2) => detectedAgents.find((d2) => d2.id === a2)?.name).join(", ")}`);
|
|
28114
|
+
if (summary.toCreate.length > 0) {
|
|
28115
|
+
console.log("");
|
|
28116
|
+
console.log(` ${colors.success("Files to create:")}`);
|
|
28117
|
+
for (const path of summary.toCreate) {
|
|
28118
|
+
console.log(` ${colors.dim("•")} ${path}`);
|
|
28119
|
+
}
|
|
28120
|
+
}
|
|
28121
|
+
if (summary.toUpdate.length > 0) {
|
|
28122
|
+
console.log("");
|
|
28123
|
+
console.log(` ${colors.info("Files to update:")}`);
|
|
28124
|
+
for (const path of summary.toUpdate) {
|
|
28125
|
+
console.log(` ${colors.dim("•")} ${path}`);
|
|
28126
|
+
}
|
|
28127
|
+
}
|
|
28128
|
+
if (summary.toSkip.length > 0 && !options.force) {
|
|
28129
|
+
console.log("");
|
|
28130
|
+
console.log(` ${colors.dim("Files to skip (already exist):")}`);
|
|
28131
|
+
for (const path of summary.toSkip) {
|
|
28132
|
+
console.log(` ${colors.dim("•")} ${path}`);
|
|
28133
|
+
}
|
|
28134
|
+
}
|
|
28135
|
+
console.log("");
|
|
28136
|
+
const shouldProceed = await me({
|
|
28137
|
+
message: "Proceed with setup?",
|
|
28138
|
+
initialValue: true
|
|
28139
|
+
});
|
|
28140
|
+
if (BD(shouldProceed) || !shouldProceed) {
|
|
28141
|
+
ve("Setup cancelled");
|
|
28142
|
+
process.exit(0);
|
|
28143
|
+
}
|
|
28144
|
+
console.log("");
|
|
28145
|
+
await writeFilesWithProgress(allFiles, { force: options.force });
|
|
28146
|
+
console.log("");
|
|
28147
|
+
fe(colors.success("Setup complete!"));
|
|
28148
|
+
console.log("");
|
|
28149
|
+
console.log(colors.bold(" Next steps:"));
|
|
28150
|
+
console.log("");
|
|
28151
|
+
if (selectedAgents.includes("claude")) {
|
|
28152
|
+
console.log(` ${colors.brand("Claude Code:")}`);
|
|
28153
|
+
console.log(` Run: ${colors.highlight("/hmy #42")} or ${colors.highlight('/hmy "Fix login bug"')}`);
|
|
28154
|
+
console.log("");
|
|
28155
|
+
}
|
|
28156
|
+
if (selectedAgents.includes("codex")) {
|
|
28157
|
+
console.log(` ${colors.brand("Codex:")}`);
|
|
28158
|
+
console.log(` Run: ${colors.highlight("/prompts:hmy #42")}`);
|
|
28159
|
+
console.log("");
|
|
28160
|
+
}
|
|
28161
|
+
if (selectedAgents.includes("cursor")) {
|
|
28162
|
+
console.log(` ${colors.brand("Cursor:")}`);
|
|
28163
|
+
console.log(` MCP tools available automatically. Mention card references to activate.`);
|
|
28164
|
+
console.log("");
|
|
28165
|
+
}
|
|
28166
|
+
if (selectedAgents.includes("windsurf")) {
|
|
28167
|
+
console.log(` ${colors.brand("Windsurf:")}`);
|
|
28168
|
+
console.log(` MCP tools available automatically. Mention card references to activate.`);
|
|
28169
|
+
console.log("");
|
|
28170
|
+
}
|
|
28171
|
+
console.log(` ${colors.dim("Need help? Visit https://gethmy.com/docs/mcp")}`);
|
|
28172
|
+
console.log("");
|
|
28173
|
+
}
|
|
28174
|
+
|
|
26629
28175
|
// src/cli.ts
|
|
26630
|
-
var rl =
|
|
28176
|
+
var rl = createInterface2({
|
|
26631
28177
|
input: process.stdin,
|
|
26632
28178
|
output: process.stdout
|
|
26633
28179
|
});
|
|
@@ -26643,10 +28189,11 @@ program.command("serve").description("Start the MCP server (stdio transport)").a
|
|
|
26643
28189
|
const server = new HarmonyMCPServer;
|
|
26644
28190
|
await server.run();
|
|
26645
28191
|
});
|
|
26646
|
-
program.command("configure").description("Configure the MCP server with your Harmony API key").option("-k, --api-key <key>", "API key (generate at gethmy.com → Settings → API Keys)").option("-u, --api-url <url>", "API URL (optional, for self-hosted instances)").action(async (options) => {
|
|
28192
|
+
program.command("configure").description("Configure the MCP server with your Harmony API key").option("-k, --api-key <key>", "API key (generate at gethmy.com → Settings → API Keys)").option("-u, --api-url <url>", "API URL (optional, for self-hosted instances)").option("-e, --user-email <email>", "Your email for auto-assignment when starting agent sessions").action(async (options) => {
|
|
26647
28193
|
try {
|
|
26648
28194
|
let apiKey = options.apiKey;
|
|
26649
28195
|
let apiUrl = options.apiUrl;
|
|
28196
|
+
let userEmail = options.userEmail;
|
|
26650
28197
|
if (!apiKey) {
|
|
26651
28198
|
console.log(`Configure Harmony MCP Server
|
|
26652
28199
|
`);
|
|
@@ -26663,10 +28210,16 @@ program.command("configure").description("Configure the MCP server with your Har
|
|
|
26663
28210
|
if (apiUrl) {
|
|
26664
28211
|
config2.apiUrl = apiUrl;
|
|
26665
28212
|
}
|
|
28213
|
+
if (userEmail) {
|
|
28214
|
+
config2.userEmail = userEmail;
|
|
28215
|
+
}
|
|
26666
28216
|
saveConfig(config2);
|
|
26667
28217
|
console.log(`
|
|
26668
28218
|
Configuration saved successfully!`);
|
|
26669
28219
|
console.log(`Config file: ${getConfigPath()}`);
|
|
28220
|
+
if (userEmail) {
|
|
28221
|
+
console.log(`User email: ${userEmail}`);
|
|
28222
|
+
}
|
|
26670
28223
|
console.log(`
|
|
26671
28224
|
You can now use the MCP server with Claude Code.`);
|
|
26672
28225
|
console.log(`Add this to your ~/.claude/settings.json:
|
|
@@ -26690,10 +28243,17 @@ program.command("status").description("Show configuration status").action(() =>
|
|
|
26690
28243
|
const globalConfig2 = loadConfig();
|
|
26691
28244
|
const localConfig = loadLocalConfig();
|
|
26692
28245
|
const hasLocal = hasLocalConfig();
|
|
28246
|
+
const maskEmail = (email2) => {
|
|
28247
|
+
const [local, domain] = email2.split("@");
|
|
28248
|
+
if (!domain)
|
|
28249
|
+
return email2;
|
|
28250
|
+
return `${local[0]}***@${domain}`;
|
|
28251
|
+
};
|
|
26693
28252
|
if (isConfigured()) {
|
|
26694
28253
|
console.log("Status: Configured");
|
|
26695
28254
|
console.log(`API Key: ${globalConfig2.apiKey?.slice(0, 8)}...`);
|
|
26696
28255
|
console.log(`API URL: ${globalConfig2.apiUrl}`);
|
|
28256
|
+
console.log(`User Email: ${globalConfig2.userEmail ? maskEmail(globalConfig2.userEmail) : "(not set)"}`);
|
|
26697
28257
|
console.log(`
|
|
26698
28258
|
Global Context:`);
|
|
26699
28259
|
console.log(` Workspace: ${globalConfig2.activeWorkspaceId || "(not set)"}`);
|
|
@@ -26728,7 +28288,8 @@ program.command("reset").description("Remove stored configuration").action(() =>
|
|
|
26728
28288
|
saveConfig({
|
|
26729
28289
|
apiKey: null,
|
|
26730
28290
|
activeWorkspaceId: null,
|
|
26731
|
-
activeProjectId: null
|
|
28291
|
+
activeProjectId: null,
|
|
28292
|
+
userEmail: null
|
|
26732
28293
|
});
|
|
26733
28294
|
console.log("Configuration reset successfully");
|
|
26734
28295
|
});
|
|
@@ -26752,7 +28313,31 @@ program.command("set-project <projectId>").description("Set the active project c
|
|
|
26752
28313
|
console.log(`Global project set to: ${projectId}`);
|
|
26753
28314
|
}
|
|
26754
28315
|
});
|
|
26755
|
-
program.command("
|
|
28316
|
+
program.command("set-user-email <email>").description("Set your email for auto-assignment when starting agent sessions").action((email2) => {
|
|
28317
|
+
if (!email2.includes("@") || !email2.includes(".")) {
|
|
28318
|
+
console.error("Error: Invalid email format");
|
|
28319
|
+
process.exit(1);
|
|
28320
|
+
}
|
|
28321
|
+
setUserEmail(email2);
|
|
28322
|
+
console.log(`User email set to: ${email2}`);
|
|
28323
|
+
console.log(`
|
|
28324
|
+
Cards will be automatically assigned to you when starting agent sessions.`);
|
|
28325
|
+
});
|
|
28326
|
+
program.command("clear-user-email").description("Clear the configured user email (disables auto-assignment)").action(() => {
|
|
28327
|
+
setUserEmail(null);
|
|
28328
|
+
console.log("User email cleared");
|
|
28329
|
+
console.log(`
|
|
28330
|
+
Auto-assignment is now disabled.`);
|
|
28331
|
+
});
|
|
28332
|
+
program.command("setup").description("Interactive setup wizard for Harmony MCP (recommended)").option("-f, --force", "Overwrite existing configuration files").option("-k, --api-key <key>", "API key (skips prompt)").option("-a, --agent <agents...>", "Agent(s) to configure: claude, codex, cursor, windsurf").action(async (options) => {
|
|
28333
|
+
rl.close();
|
|
28334
|
+
await runSetup({
|
|
28335
|
+
force: options.force,
|
|
28336
|
+
apiKey: options.apiKey,
|
|
28337
|
+
agents: options.agent
|
|
28338
|
+
});
|
|
28339
|
+
});
|
|
28340
|
+
program.command("init").description('Initialize Harmony MCP for AI coding agents (use "setup" for interactive wizard)').option("-a, --agent <agents...>", `Agent(s) to configure: ${SUPPORTED_AGENTS.join(", ")}`).option("--all", "Configure all supported agents").option("--detect", "Auto-detect installed agents and configure them").option("-f, --force", "Overwrite existing configuration files").option("-d, --directory <path>", "Project directory (default: current directory)").option("-w, --workspace <id>", "Set local workspace context for this project").option("-p, --project <id>", "Set local project context for this project").action(async (options) => {
|
|
26756
28341
|
console.log(`Harmony MCP Initialization
|
|
26757
28342
|
`);
|
|
26758
28343
|
let agents = [];
|
|
@@ -26773,8 +28358,8 @@ Use --all to configure all agents, or --agent to specify specific ones.`);
|
|
|
26773
28358
|
console.log(`Detected agents: ${agents.join(", ")}
|
|
26774
28359
|
`);
|
|
26775
28360
|
} else if (options.agent) {
|
|
26776
|
-
agents = options.agent.filter((
|
|
26777
|
-
const invalid = options.agent.filter((
|
|
28361
|
+
agents = options.agent.filter((a2) => SUPPORTED_AGENTS.includes(a2));
|
|
28362
|
+
const invalid = options.agent.filter((a2) => !SUPPORTED_AGENTS.includes(a2));
|
|
26778
28363
|
if (invalid.length > 0) {
|
|
26779
28364
|
console.log(`Warning: Unknown agent(s) ignored: ${invalid.join(", ")}`);
|
|
26780
28365
|
}
|
|
@@ -26840,11 +28425,11 @@ ${result.agent.toUpperCase()}:`);
|
|
|
26840
28425
|
}
|
|
26841
28426
|
if (result.filesCreated.length > 0) {
|
|
26842
28427
|
console.log(" Created:");
|
|
26843
|
-
result.filesCreated.forEach((
|
|
28428
|
+
result.filesCreated.forEach((f2) => console.log(` ✓ ${f2}`));
|
|
26844
28429
|
}
|
|
26845
28430
|
if (result.filesSkipped.length > 0) {
|
|
26846
28431
|
console.log(" Skipped (already exists, use --force to overwrite):");
|
|
26847
|
-
result.filesSkipped.forEach((
|
|
28432
|
+
result.filesSkipped.forEach((f2) => console.log(` - ${f2}`));
|
|
26848
28433
|
}
|
|
26849
28434
|
if (result.filesCreated.length === 0 && result.filesSkipped.length === 0) {
|
|
26850
28435
|
console.log(" No changes made");
|