@wix/web50-cli 0.1.0 → 0.1.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/cjs/auth/deviceFlow.js +99 -13
- package/dist/cjs/auth/deviceFlow.js.map +1 -1
- package/dist/cjs/auth/index.js +65 -12
- package/dist/cjs/auth/index.js.map +1 -1
- package/dist/cjs/auth/secretStore.js.map +1 -1
- package/dist/cjs/cli.js +29 -1
- package/dist/cjs/cli.js.map +1 -1
- package/dist/cjs/commands/bundle.js +95 -0
- package/dist/cjs/commands/bundle.js.map +1 -0
- package/dist/cjs/commands/conversation.js +50 -0
- package/dist/cjs/commands/conversation.js.map +1 -0
- package/dist/cjs/commands/conversationWizard.js +526 -0
- package/dist/cjs/commands/conversationWizard.js.map +1 -0
- package/dist/cjs/commands/deploy.js +192 -0
- package/dist/cjs/commands/deploy.js.map +1 -0
- package/dist/cjs/commands/embed.js +118 -0
- package/dist/cjs/commands/embed.js.map +1 -0
- package/dist/cjs/commands/getClientId.js +60 -0
- package/dist/cjs/commands/getClientId.js.map +1 -0
- package/dist/cjs/commands/init.js +31 -26
- package/dist/cjs/commands/init.js.map +1 -1
- package/dist/cjs/commands/instructions.js +360 -0
- package/dist/cjs/commands/instructions.js.map +1 -0
- package/dist/cjs/commands/login.js +59 -4
- package/dist/cjs/commands/login.js.map +1 -1
- package/dist/cjs/commands/logout.js +16 -0
- package/dist/cjs/commands/logout.js.map +1 -0
- package/dist/cjs/commands/serve.js +122 -0
- package/dist/cjs/commands/serve.js.map +1 -0
- package/dist/cjs/commands/storybook.js +102 -0
- package/dist/cjs/commands/storybook.js.map +1 -0
- package/dist/cjs/commands/validate.js +266 -18
- package/dist/cjs/commands/validate.js.map +1 -1
- package/dist/cjs/commands/whoami.js +48 -0
- package/dist/cjs/commands/whoami.js.map +1 -0
- package/dist/cjs/utils/print.js +12 -0
- package/dist/cjs/utils/print.js.map +1 -1
- package/dist/cjs/utils/project.js +11 -0
- package/dist/cjs/utils/project.js.map +1 -1
- package/dist/cjs/utils/wixApi.js +55 -0
- package/dist/cjs/utils/wixApi.js.map +1 -0
- package/dist/esm/auth/deviceFlow.js +106 -13
- package/dist/esm/auth/deviceFlow.js.map +1 -1
- package/dist/esm/auth/index.js +71 -13
- package/dist/esm/auth/index.js.map +1 -1
- package/dist/esm/auth/secretStore.js.map +1 -1
- package/dist/esm/cli.js +29 -1
- package/dist/esm/cli.js.map +1 -1
- package/dist/esm/commands/bundle.js +92 -0
- package/dist/esm/commands/bundle.js.map +1 -0
- package/dist/esm/commands/conversation.js +44 -0
- package/dist/esm/commands/conversation.js.map +1 -0
- package/dist/esm/commands/conversationWizard.js +527 -0
- package/dist/esm/commands/conversationWizard.js.map +1 -0
- package/dist/esm/commands/deploy.js +194 -0
- package/dist/esm/commands/deploy.js.map +1 -0
- package/dist/esm/commands/embed.js +112 -0
- package/dist/esm/commands/embed.js.map +1 -0
- package/dist/esm/commands/getClientId.js +56 -0
- package/dist/esm/commands/getClientId.js.map +1 -0
- package/dist/esm/commands/init.js +32 -27
- package/dist/esm/commands/init.js.map +1 -1
- package/dist/esm/commands/instructions.js +360 -0
- package/dist/esm/commands/instructions.js.map +1 -0
- package/dist/esm/commands/login.js +62 -6
- package/dist/esm/commands/login.js.map +1 -1
- package/dist/esm/commands/logout.js +12 -0
- package/dist/esm/commands/logout.js.map +1 -0
- package/dist/esm/commands/serve.js +117 -0
- package/dist/esm/commands/serve.js.map +1 -0
- package/dist/esm/commands/storybook.js +97 -0
- package/dist/esm/commands/storybook.js.map +1 -0
- package/dist/esm/commands/validate.js +269 -19
- package/dist/esm/commands/validate.js.map +1 -1
- package/dist/esm/commands/whoami.js +44 -0
- package/dist/esm/commands/whoami.js.map +1 -0
- package/dist/esm/utils/print.js +10 -0
- package/dist/esm/utils/print.js.map +1 -1
- package/dist/esm/utils/project.js +8 -0
- package/dist/esm/utils/project.js.map +1 -1
- package/dist/esm/utils/wixApi.js +51 -0
- package/dist/esm/utils/wixApi.js.map +1 -0
- package/dist/types/auth/deviceFlow.d.ts +3 -1
- package/dist/types/auth/deviceFlow.d.ts.map +1 -1
- package/dist/types/auth/index.d.ts +5 -1
- package/dist/types/auth/index.d.ts.map +1 -1
- package/dist/types/auth/secretStore.d.ts +2 -0
- package/dist/types/auth/secretStore.d.ts.map +1 -1
- package/dist/types/commands/bundle.d.ts +10 -0
- package/dist/types/commands/bundle.d.ts.map +1 -0
- package/dist/types/commands/conversation.d.ts +3 -0
- package/dist/types/commands/conversation.d.ts.map +1 -0
- package/dist/types/commands/conversationWizard.d.ts +3 -0
- package/dist/types/commands/conversationWizard.d.ts.map +1 -0
- package/dist/types/commands/deploy.d.ts +3 -0
- package/dist/types/commands/deploy.d.ts.map +1 -0
- package/dist/types/commands/embed.d.ts +3 -0
- package/dist/types/commands/embed.d.ts.map +1 -0
- package/dist/types/commands/getClientId.d.ts +3 -0
- package/dist/types/commands/getClientId.d.ts.map +1 -0
- package/dist/types/commands/init.d.ts.map +1 -1
- package/dist/types/commands/instructions.d.ts +3 -0
- package/dist/types/commands/instructions.d.ts.map +1 -0
- package/dist/types/commands/login.d.ts.map +1 -1
- package/dist/types/commands/logout.d.ts +3 -0
- package/dist/types/commands/logout.d.ts.map +1 -0
- package/dist/types/commands/serve.d.ts +3 -0
- package/dist/types/commands/serve.d.ts.map +1 -0
- package/dist/types/commands/storybook.d.ts +3 -0
- package/dist/types/commands/storybook.d.ts.map +1 -0
- package/dist/types/commands/validate.d.ts +5 -0
- package/dist/types/commands/validate.d.ts.map +1 -1
- package/dist/types/commands/whoami.d.ts +3 -0
- package/dist/types/commands/whoami.d.ts.map +1 -0
- package/dist/types/utils/print.d.ts +3 -0
- package/dist/types/utils/print.d.ts.map +1 -1
- package/dist/types/utils/project.d.ts +10 -0
- package/dist/types/utils/project.d.ts.map +1 -1
- package/dist/types/utils/wixApi.d.ts +9 -0
- package/dist/types/utils/wixApi.d.ts.map +1 -0
- package/package.json +5 -5
- package/defaults/package.json +0 -42
|
@@ -0,0 +1,50 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault");
|
|
4
|
+
exports.__esModule = true;
|
|
5
|
+
exports.conversationCommand = void 0;
|
|
6
|
+
var _commander = require("commander");
|
|
7
|
+
var readline = _interopRequireWildcard(require("readline"));
|
|
8
|
+
var _chalk = _interopRequireDefault(require("chalk"));
|
|
9
|
+
var _wixApi = require("../utils/wixApi");
|
|
10
|
+
function _interopRequireWildcard(e, t) { if ("function" == typeof WeakMap) var r = new WeakMap(), n = new WeakMap(); return (_interopRequireWildcard = function (e, t) { if (!t && e && e.__esModule) return e; var o, i, f = { __proto__: null, default: e }; if (null === e || "object" != typeof e && "function" != typeof e) return f; if (o = t ? n : r) { if (o.has(e)) return o.get(e); o.set(e, f); } for (const t in e) "default" !== t && {}.hasOwnProperty.call(e, t) && ((i = (o = Object.defineProperty) && Object.getOwnPropertyDescriptor(e, t)) && (i.get || i.set) ? o(f, t, i) : f[t] = e[t]); return f; })(e, t); }
|
|
11
|
+
async function promptForTid() {
|
|
12
|
+
const rl = readline.createInterface({
|
|
13
|
+
input: process.stdin,
|
|
14
|
+
output: process.stdout
|
|
15
|
+
});
|
|
16
|
+
return new Promise(resolve => {
|
|
17
|
+
rl.question('Enter trigger ID (TID): ', answer => {
|
|
18
|
+
rl.close();
|
|
19
|
+
resolve(answer.trim());
|
|
20
|
+
});
|
|
21
|
+
});
|
|
22
|
+
}
|
|
23
|
+
const getCmd = new _commander.Command('get').description('Get a conversation by trigger ID').option('--id <uuid>', 'Trigger ID (TID)').action(async opts => {
|
|
24
|
+
try {
|
|
25
|
+
const tid = opts.id || (await promptForTid());
|
|
26
|
+
if (!tid) {
|
|
27
|
+
console.error('Error: trigger ID is required');
|
|
28
|
+
process.exit(1);
|
|
29
|
+
}
|
|
30
|
+
const data = await (0, _wixApi.wixRequest)({
|
|
31
|
+
path: `/_api/conversation-history/v1/conversations/by-trigger/${tid}`
|
|
32
|
+
});
|
|
33
|
+
const messages = data.messages ?? [];
|
|
34
|
+
if (messages.length === 0) {
|
|
35
|
+
console.log('(no messages)');
|
|
36
|
+
return;
|
|
37
|
+
}
|
|
38
|
+
for (const msg of messages) {
|
|
39
|
+
const role = msg.role === 'user' ? _chalk.default.cyan('user: ') : _chalk.default.green('assistant:');
|
|
40
|
+
console.log(role);
|
|
41
|
+
console.log(msg.content ?? '(empty)');
|
|
42
|
+
console.log();
|
|
43
|
+
}
|
|
44
|
+
} catch (err) {
|
|
45
|
+
console.error('Error:', err.message);
|
|
46
|
+
process.exit(1);
|
|
47
|
+
}
|
|
48
|
+
});
|
|
49
|
+
const conversationCommand = exports.conversationCommand = new _commander.Command('conversation').description('Conversation history commands').addCommand(getCmd);
|
|
50
|
+
//# sourceMappingURL=conversation.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"names":["_commander","require","readline","_interopRequireWildcard","_chalk","_interopRequireDefault","_wixApi","e","t","WeakMap","r","n","__esModule","o","i","f","__proto__","default","has","get","set","hasOwnProperty","call","Object","defineProperty","getOwnPropertyDescriptor","promptForTid","rl","createInterface","input","process","stdin","output","stdout","Promise","resolve","question","answer","close","trim","getCmd","Command","description","option","action","opts","tid","id","console","error","exit","data","wixRequest","path","messages","length","log","msg","role","chalk","cyan","green","content","err","message","conversationCommand","exports","addCommand"],"sources":["../../../src/commands/conversation.ts"],"sourcesContent":["import { Command } from 'commander';\nimport * as readline from 'readline';\nimport chalk from 'chalk';\nimport { wixRequest } from '../utils/wixApi';\n\ninterface ConversationMessage {\n role?: string;\n content?: string;\n createdDate?: string;\n}\n\ninterface ConversationDetail {\n messages?: ConversationMessage[];\n [key: string]: unknown;\n}\n\nasync function promptForTid(): Promise<string> {\n const rl = readline.createInterface({\n input: process.stdin,\n output: process.stdout,\n });\n return new Promise((resolve) => {\n rl.question('Enter trigger ID (TID): ', (answer) => {\n rl.close();\n resolve(answer.trim());\n });\n });\n}\n\nconst getCmd = new Command('get')\n .description('Get a conversation by trigger ID')\n .option('--id <uuid>', 'Trigger ID (TID)')\n .action(async (opts) => {\n try {\n const tid: string = opts.id || (await promptForTid());\n if (!tid) {\n console.error('Error: trigger ID is required');\n process.exit(1);\n }\n\n const data = await wixRequest<ConversationDetail>({\n path: `/_api/conversation-history/v1/conversations/by-trigger/${tid}`,\n });\n\n const messages = data.messages ?? [];\n if (messages.length === 0) {\n console.log('(no messages)');\n return;\n }\n for (const msg of messages) {\n const role = msg.role === 'user' ? chalk.cyan('user: ') : chalk.green('assistant:');\n console.log(role);\n console.log(msg.content ?? '(empty)');\n console.log();\n }\n } catch (err) {\n console.error('Error:', (err as Error).message);\n process.exit(1);\n }\n });\n\nexport const conversationCommand = new Command('conversation')\n .description('Conversation history commands')\n .addCommand(getCmd);\n"],"mappings":"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","ignoreList":[]}
|
|
@@ -0,0 +1,526 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault");
|
|
4
|
+
exports.__esModule = true;
|
|
5
|
+
exports.conversationsCommand = void 0;
|
|
6
|
+
var _commander = require("commander");
|
|
7
|
+
var readline = _interopRequireWildcard(require("readline"));
|
|
8
|
+
var fs = _interopRequireWildcard(require("fs"));
|
|
9
|
+
var path = _interopRequireWildcard(require("path"));
|
|
10
|
+
var _inquirer = _interopRequireDefault(require("inquirer"));
|
|
11
|
+
var _chalk = _interopRequireDefault(require("chalk"));
|
|
12
|
+
var _ora = _interopRequireDefault(require("ora"));
|
|
13
|
+
var _open = _interopRequireDefault(require("open"));
|
|
14
|
+
var _wixApi = require("../utils/wixApi");
|
|
15
|
+
function _interopRequireWildcard(e, t) { if ("function" == typeof WeakMap) var r = new WeakMap(), n = new WeakMap(); return (_interopRequireWildcard = function (e, t) { if (!t && e && e.__esModule) return e; var o, i, f = { __proto__: null, default: e }; if (null === e || "object" != typeof e && "function" != typeof e) return f; if (o = t ? n : r) { if (o.has(e)) return o.get(e); o.set(e, f); } for (const t in e) "default" !== t && {}.hasOwnProperty.call(e, t) && ((i = (o = Object.defineProperty) && Object.getOwnPropertyDescriptor(e, t)) && (i.get || i.set) ? o(f, t, i) : f[t] = e[t]); return f; })(e, t); }
|
|
16
|
+
// ── API response shapes ────────────────────────────────────────────────────
|
|
17
|
+
|
|
18
|
+
// ── Verbose flag ───────────────────────────────────────────────────────────
|
|
19
|
+
|
|
20
|
+
let verbose = false;
|
|
21
|
+
|
|
22
|
+
// ── Wizard state ───────────────────────────────────────────────────────────
|
|
23
|
+
|
|
24
|
+
// ── UI primitives ──────────────────────────────────────────────────────────
|
|
25
|
+
|
|
26
|
+
const BOX_W = 66;
|
|
27
|
+
|
|
28
|
+
/** Double-border header box — visually distinct section for breadcrumbs */
|
|
29
|
+
function printHeader(breadcrumb) {
|
|
30
|
+
const pad = ' '.repeat(Math.max(0, BOX_W - breadcrumb.length - 1));
|
|
31
|
+
console.log(_chalk.default.cyan('╔' + '═'.repeat(BOX_W) + '╗'));
|
|
32
|
+
console.log(`${_chalk.default.cyan('║')} ${_chalk.default.bold(breadcrumb)}${pad}${_chalk.default.cyan('║')}`);
|
|
33
|
+
console.log(_chalk.default.cyan('╚' + '═'.repeat(BOX_W) + '╝'));
|
|
34
|
+
console.log();
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
/** Thin separator line with inline hint text */
|
|
38
|
+
function printFooterHints(hints) {
|
|
39
|
+
const line = '─'.repeat(BOX_W + 2);
|
|
40
|
+
console.log(_chalk.default.dim(line));
|
|
41
|
+
console.log(_chalk.default.dim(` ${hints}`));
|
|
42
|
+
console.log();
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
// ── Time helpers ───────────────────────────────────────────────────────────
|
|
46
|
+
|
|
47
|
+
function timeAgo(iso) {
|
|
48
|
+
if (!iso) {
|
|
49
|
+
return 'unknown';
|
|
50
|
+
}
|
|
51
|
+
const diff = Date.now() - new Date(iso).getTime();
|
|
52
|
+
const mins = Math.floor(diff / 60_000);
|
|
53
|
+
const hours = Math.floor(diff / 3_600_000);
|
|
54
|
+
const days = Math.floor(diff / 86_400_000);
|
|
55
|
+
if (mins < 1) {
|
|
56
|
+
return 'just now';
|
|
57
|
+
}
|
|
58
|
+
if (mins < 60) {
|
|
59
|
+
return `${mins}m ago`;
|
|
60
|
+
}
|
|
61
|
+
if (hours < 24) {
|
|
62
|
+
return `${hours}h ago`;
|
|
63
|
+
}
|
|
64
|
+
return `${days}d ago`;
|
|
65
|
+
}
|
|
66
|
+
function formatTime(iso) {
|
|
67
|
+
if (!iso) {
|
|
68
|
+
return '??:??';
|
|
69
|
+
}
|
|
70
|
+
try {
|
|
71
|
+
return new Date(iso).toLocaleTimeString([], {
|
|
72
|
+
hour: '2-digit',
|
|
73
|
+
minute: '2-digit'
|
|
74
|
+
});
|
|
75
|
+
} catch {
|
|
76
|
+
return iso;
|
|
77
|
+
}
|
|
78
|
+
}
|
|
79
|
+
function truncate(text, max = 50) {
|
|
80
|
+
const clean = text.replace(/\n/g, ' ').replace(/<!--.*?-->/g, '').trim();
|
|
81
|
+
return clean.length > max ? `${clean.slice(0, max - 1)}…` : clean;
|
|
82
|
+
}
|
|
83
|
+
|
|
84
|
+
// ── Markdown renderer ──────────────────────────────────────────────────────
|
|
85
|
+
|
|
86
|
+
function renderMarkdownLine(line) {
|
|
87
|
+
const h3 = line.match(/^### (.+)/);
|
|
88
|
+
if (h3) {
|
|
89
|
+
return _chalk.default.bold.underline(h3[1]);
|
|
90
|
+
}
|
|
91
|
+
const h2 = line.match(/^## (.+)/);
|
|
92
|
+
if (h2) {
|
|
93
|
+
return _chalk.default.bold.underline(h2[1]);
|
|
94
|
+
}
|
|
95
|
+
const h1 = line.match(/^# (.+)/);
|
|
96
|
+
if (h1) {
|
|
97
|
+
return _chalk.default.bold.underline(h1[1]);
|
|
98
|
+
}
|
|
99
|
+
return line.replace(/\*\*(.+?)\*\*/g, (_, t) => _chalk.default.bold(t)).replace(/`([^`]+)`/g, (_, t) => _chalk.default.yellow(t));
|
|
100
|
+
}
|
|
101
|
+
function renderMarkdown(text) {
|
|
102
|
+
return text.split('\n').map(renderMarkdownLine).join('\n');
|
|
103
|
+
}
|
|
104
|
+
function pressEnterToContinue() {
|
|
105
|
+
const rl = readline.createInterface({
|
|
106
|
+
input: process.stdin,
|
|
107
|
+
output: process.stdout
|
|
108
|
+
});
|
|
109
|
+
return new Promise(resolve => {
|
|
110
|
+
rl.question(_chalk.default.dim('\nPress Enter to go back…'), () => {
|
|
111
|
+
rl.close();
|
|
112
|
+
resolve();
|
|
113
|
+
});
|
|
114
|
+
});
|
|
115
|
+
}
|
|
116
|
+
|
|
117
|
+
// ── Row builder ────────────────────────────────────────────────────────────
|
|
118
|
+
|
|
119
|
+
/** Builds a single list row: 🕒 HH:MM (Nm ago) │ message text */
|
|
120
|
+
function buildRow(createdDate, label) {
|
|
121
|
+
const time = _chalk.default.dim(`🕒 ${formatTime(createdDate)}`);
|
|
122
|
+
const ago = _chalk.default.dim(`(${timeAgo(createdDate)})`);
|
|
123
|
+
const divider = _chalk.default.dim(' │ ');
|
|
124
|
+
const text = _chalk.default.white(truncate(label, 42));
|
|
125
|
+
return ` ${time} ${ago}${divider}${text}`;
|
|
126
|
+
}
|
|
127
|
+
|
|
128
|
+
// ── Screens ────────────────────────────────────────────────────────────────
|
|
129
|
+
|
|
130
|
+
async function showRootsScreen() {
|
|
131
|
+
const spinner = (0, _ora.default)('Fetching conversations…').start();
|
|
132
|
+
let roots = [];
|
|
133
|
+
try {
|
|
134
|
+
const data = await (0, _wixApi.wixRequest)({
|
|
135
|
+
path: '/web5/conversations/cli/roots/query',
|
|
136
|
+
method: 'POST',
|
|
137
|
+
body: {},
|
|
138
|
+
verbose
|
|
139
|
+
});
|
|
140
|
+
spinner.stop();
|
|
141
|
+
roots = data.messages ?? [];
|
|
142
|
+
} catch (err) {
|
|
143
|
+
spinner.fail('Failed to fetch conversations');
|
|
144
|
+
console.error(_chalk.default.red(err.message));
|
|
145
|
+
await pressEnterToContinue();
|
|
146
|
+
return {
|
|
147
|
+
type: 'roots'
|
|
148
|
+
};
|
|
149
|
+
}
|
|
150
|
+
if (roots.length === 0) {
|
|
151
|
+
console.clear();
|
|
152
|
+
console.log(_chalk.default.yellow('No conversations found.'));
|
|
153
|
+
await pressEnterToContinue();
|
|
154
|
+
return {
|
|
155
|
+
type: 'exit'
|
|
156
|
+
};
|
|
157
|
+
}
|
|
158
|
+
console.clear();
|
|
159
|
+
printHeader(`📁 Conversations ${_chalk.default.dim(`${roots.length} total`)}`);
|
|
160
|
+
printFooterHints('[↑↓] Navigate [Enter] Select [Ctrl+C] Quit');
|
|
161
|
+
const choices = [...roots.map((r, i) => ({
|
|
162
|
+
name: buildRow(r.createdDate, r.triggerIdContent ?? r.text ?? r.content ?? '(no content)'),
|
|
163
|
+
value: i
|
|
164
|
+
})), new _inquirer.default.Separator('─'.repeat(BOX_W)), {
|
|
165
|
+
name: ` ${_chalk.default.red('✕ Exit')}`,
|
|
166
|
+
value: -1
|
|
167
|
+
}];
|
|
168
|
+
const {
|
|
169
|
+
rootIndex
|
|
170
|
+
} = await _inquirer.default.prompt([{
|
|
171
|
+
type: 'list',
|
|
172
|
+
name: 'rootIndex',
|
|
173
|
+
message: _chalk.default.bold('Select a conversation'),
|
|
174
|
+
choices,
|
|
175
|
+
pageSize: 12
|
|
176
|
+
}]);
|
|
177
|
+
if (rootIndex === -1) {
|
|
178
|
+
return {
|
|
179
|
+
type: 'exit'
|
|
180
|
+
};
|
|
181
|
+
}
|
|
182
|
+
const selected = roots[rootIndex];
|
|
183
|
+
return {
|
|
184
|
+
type: 'messages',
|
|
185
|
+
messageId: selected.id ?? '',
|
|
186
|
+
userQuery: selected.triggerIdContent ?? '',
|
|
187
|
+
conversationId: selected.conversationId ?? ''
|
|
188
|
+
};
|
|
189
|
+
}
|
|
190
|
+
async function showMessagesScreen(messageId, userQuery, conversationId) {
|
|
191
|
+
if (!messageId) {
|
|
192
|
+
console.error(_chalk.default.red('No message ID — returning to root list.'));
|
|
193
|
+
await pressEnterToContinue();
|
|
194
|
+
return {
|
|
195
|
+
type: 'roots'
|
|
196
|
+
};
|
|
197
|
+
}
|
|
198
|
+
const spinner = (0, _ora.default)('Loading conversation…').start();
|
|
199
|
+
let messages = [];
|
|
200
|
+
try {
|
|
201
|
+
const data = await (0, _wixApi.wixRequest)({
|
|
202
|
+
path: `/web5/conversations/cli/by-message/${messageId}`,
|
|
203
|
+
verbose
|
|
204
|
+
});
|
|
205
|
+
spinner.stop();
|
|
206
|
+
messages = data.messages ?? [];
|
|
207
|
+
} catch (err) {
|
|
208
|
+
spinner.fail('Failed to load conversation');
|
|
209
|
+
console.error(_chalk.default.red(err.message));
|
|
210
|
+
await pressEnterToContinue();
|
|
211
|
+
return {
|
|
212
|
+
type: 'roots'
|
|
213
|
+
};
|
|
214
|
+
}
|
|
215
|
+
if (messages.length === 0) {
|
|
216
|
+
console.clear();
|
|
217
|
+
console.log(_chalk.default.yellow('No messages in this conversation.'));
|
|
218
|
+
await pressEnterToContinue();
|
|
219
|
+
return {
|
|
220
|
+
type: 'roots'
|
|
221
|
+
};
|
|
222
|
+
}
|
|
223
|
+
console.clear();
|
|
224
|
+
const convLabel = conversationId || messageId.slice(0, 12) + '…';
|
|
225
|
+
printHeader(`📁 Conversations ❯ 💬 ${convLabel} ${_chalk.default.dim(`${messages.length} messages`)}`);
|
|
226
|
+
printFooterHints('[↑↓] Navigate [Enter] Expand [Ctrl+C] Quit');
|
|
227
|
+
const choices = messages.map((msg, i) => ({
|
|
228
|
+
name: buildRow(msg.createdDate, msg.triggerIdContent ?? msg.content ?? '(no query)'),
|
|
229
|
+
value: i
|
|
230
|
+
}));
|
|
231
|
+
choices.push(new _inquirer.default.Separator('─'.repeat(BOX_W)));
|
|
232
|
+
choices.push({
|
|
233
|
+
name: ` ${_chalk.default.dim('← Back')}`,
|
|
234
|
+
value: -1
|
|
235
|
+
});
|
|
236
|
+
choices.push({
|
|
237
|
+
name: ` ${_chalk.default.red('✕ Exit')}`,
|
|
238
|
+
value: -2
|
|
239
|
+
});
|
|
240
|
+
const {
|
|
241
|
+
msgIndex
|
|
242
|
+
} = await _inquirer.default.prompt([{
|
|
243
|
+
type: 'list',
|
|
244
|
+
name: 'msgIndex',
|
|
245
|
+
message: _chalk.default.bold('Select a message to expand'),
|
|
246
|
+
choices,
|
|
247
|
+
pageSize: 12
|
|
248
|
+
}]);
|
|
249
|
+
if (msgIndex === -2) {
|
|
250
|
+
return {
|
|
251
|
+
type: 'exit'
|
|
252
|
+
};
|
|
253
|
+
}
|
|
254
|
+
if (msgIndex === -1) {
|
|
255
|
+
return {
|
|
256
|
+
type: 'roots'
|
|
257
|
+
};
|
|
258
|
+
}
|
|
259
|
+
return {
|
|
260
|
+
type: 'message-detail',
|
|
261
|
+
messages,
|
|
262
|
+
messageId,
|
|
263
|
+
userQuery,
|
|
264
|
+
conversationId,
|
|
265
|
+
index: msgIndex
|
|
266
|
+
};
|
|
267
|
+
}
|
|
268
|
+
async function showMessageDetailScreen(messages, index, conversationId) {
|
|
269
|
+
console.clear();
|
|
270
|
+
const msg = messages[index];
|
|
271
|
+
if (!msg) {
|
|
272
|
+
console.error(_chalk.default.red('Message not found.'));
|
|
273
|
+
return;
|
|
274
|
+
}
|
|
275
|
+
const isUser = msg.role === 'user';
|
|
276
|
+
const icon = isUser ? '👤' : '🤖';
|
|
277
|
+
const label = isUser ? 'User Query' : 'AI Response';
|
|
278
|
+
const convLabel = conversationId || 'message';
|
|
279
|
+
printHeader(`📁 Conversations ❯ 💬 ${convLabel} ❯ ${icon} ${label}`);
|
|
280
|
+
|
|
281
|
+
// Metadata row
|
|
282
|
+
console.log(_chalk.default.dim(` 🕒 ${formatTime(msg.createdDate)} (${timeAgo(msg.createdDate)})\n`));
|
|
283
|
+
|
|
284
|
+
// Content
|
|
285
|
+
const content = msg.content ?? '(empty)';
|
|
286
|
+
console.log(isUser ? _chalk.default.cyan(content) : renderMarkdown(content));
|
|
287
|
+
console.log();
|
|
288
|
+
|
|
289
|
+
// Action section
|
|
290
|
+
console.log(_chalk.default.cyan('╔' + '═'.repeat(BOX_W) + '╗'));
|
|
291
|
+
console.log(`${_chalk.default.cyan('║')} ${_chalk.default.bold('Actions')}${' '.repeat(BOX_W - 9)}${_chalk.default.cyan('║')}`);
|
|
292
|
+
console.log(_chalk.default.cyan('╚' + '═'.repeat(BOX_W) + '╝'));
|
|
293
|
+
console.log();
|
|
294
|
+
const tid = msg.triggerId ?? '';
|
|
295
|
+
const browserUrl = `https://www.copyofcircanafordemo.com/web5#tid=${tid}`;
|
|
296
|
+
const {
|
|
297
|
+
action
|
|
298
|
+
} = await _inquirer.default.prompt([{
|
|
299
|
+
type: 'list',
|
|
300
|
+
name: 'action',
|
|
301
|
+
message: _chalk.default.bold('What would you like to do?'),
|
|
302
|
+
choices: [{
|
|
303
|
+
name: ` ${_chalk.default.dim('← Back')}`,
|
|
304
|
+
value: 'back'
|
|
305
|
+
}, {
|
|
306
|
+
name: ` 🌐 Open in browser`,
|
|
307
|
+
value: 'browser'
|
|
308
|
+
}]
|
|
309
|
+
}]);
|
|
310
|
+
if (action === 'browser') {
|
|
311
|
+
await (0, _open.default)(browserUrl);
|
|
312
|
+
}
|
|
313
|
+
}
|
|
314
|
+
|
|
315
|
+
// ── Main loop ──────────────────────────────────────────────────────────────
|
|
316
|
+
|
|
317
|
+
async function runWizard(verboseFlag) {
|
|
318
|
+
verbose = verboseFlag;
|
|
319
|
+
process.on('SIGINT', () => {
|
|
320
|
+
console.log(_chalk.default.dim('\nBye.\n'));
|
|
321
|
+
process.exit(0);
|
|
322
|
+
});
|
|
323
|
+
let screen = {
|
|
324
|
+
type: 'roots'
|
|
325
|
+
};
|
|
326
|
+
let running = true;
|
|
327
|
+
while (running) {
|
|
328
|
+
switch (screen.type) {
|
|
329
|
+
case 'roots':
|
|
330
|
+
screen = await showRootsScreen();
|
|
331
|
+
break;
|
|
332
|
+
case 'messages':
|
|
333
|
+
screen = await showMessagesScreen(screen.messageId, screen.userQuery, screen.conversationId);
|
|
334
|
+
break;
|
|
335
|
+
case 'message-detail':
|
|
336
|
+
{
|
|
337
|
+
const s = screen;
|
|
338
|
+
await showMessageDetailScreen(s.messages, s.index, s.conversationId);
|
|
339
|
+
screen = {
|
|
340
|
+
type: 'messages',
|
|
341
|
+
messageId: s.messageId,
|
|
342
|
+
userQuery: s.userQuery,
|
|
343
|
+
conversationId: s.conversationId
|
|
344
|
+
};
|
|
345
|
+
break;
|
|
346
|
+
}
|
|
347
|
+
case 'exit':
|
|
348
|
+
console.clear();
|
|
349
|
+
console.log(_chalk.default.dim('Bye.\n'));
|
|
350
|
+
running = false;
|
|
351
|
+
break;
|
|
352
|
+
}
|
|
353
|
+
}
|
|
354
|
+
process.exit(0);
|
|
355
|
+
}
|
|
356
|
+
|
|
357
|
+
// ── Subcommands ────────────────────────────────────────────────────────────
|
|
358
|
+
|
|
359
|
+
// ── get ────────────────────────────────────────────────────────────────────
|
|
360
|
+
|
|
361
|
+
function printMessages(messages, format) {
|
|
362
|
+
if (messages.length === 0) {
|
|
363
|
+
console.log('(no messages)');
|
|
364
|
+
return;
|
|
365
|
+
}
|
|
366
|
+
if (format === 'json') {
|
|
367
|
+
const view = messages.map(({
|
|
368
|
+
role,
|
|
369
|
+
content,
|
|
370
|
+
createdDate
|
|
371
|
+
}) => ({
|
|
372
|
+
role,
|
|
373
|
+
content,
|
|
374
|
+
createdDate
|
|
375
|
+
}));
|
|
376
|
+
console.log(JSON.stringify(view, null, 2));
|
|
377
|
+
return;
|
|
378
|
+
}
|
|
379
|
+
for (const msg of messages) {
|
|
380
|
+
const isUser = msg.role === 'user';
|
|
381
|
+
const role = isUser ? _chalk.default.cyan('user: ') : _chalk.default.green('assistant:');
|
|
382
|
+
const time = msg.createdDate ? _chalk.default.dim(` [${formatTime(msg.createdDate)}]`) : '';
|
|
383
|
+
const text = (isUser ? msg.triggerIdContent ?? msg.content : msg.content) ?? '(empty)';
|
|
384
|
+
console.log(`${role}${time}`);
|
|
385
|
+
console.log(text);
|
|
386
|
+
console.log();
|
|
387
|
+
}
|
|
388
|
+
}
|
|
389
|
+
const getCmd = new _commander.Command('get').description('Get a conversation by message ID (--id) or trigger ID (--tid)').option('--id <id>', 'Message ID — from conversations list').option('--tid <tid>', 'Trigger ID (TID)').option('--format <format>', 'Output format: text (default) or json', 'text').action(async opts => {
|
|
390
|
+
try {
|
|
391
|
+
if (opts.id) {
|
|
392
|
+
const data = await (0, _wixApi.wixRequest)({
|
|
393
|
+
path: `/web5/conversations/cli/by-message/${opts.id}`,
|
|
394
|
+
verbose
|
|
395
|
+
});
|
|
396
|
+
printMessages(data.messages ?? [], opts.format ?? 'text');
|
|
397
|
+
return;
|
|
398
|
+
}
|
|
399
|
+
let tid = opts.tid ?? '';
|
|
400
|
+
if (!tid) {
|
|
401
|
+
const rl = readline.createInterface({
|
|
402
|
+
input: process.stdin,
|
|
403
|
+
output: process.stdout
|
|
404
|
+
});
|
|
405
|
+
tid = await new Promise(resolve => {
|
|
406
|
+
rl.question('Enter trigger ID (TID): ', answer => {
|
|
407
|
+
rl.close();
|
|
408
|
+
resolve(answer.trim());
|
|
409
|
+
});
|
|
410
|
+
});
|
|
411
|
+
}
|
|
412
|
+
if (!tid) {
|
|
413
|
+
console.error('Error: provide --id <message-id> or --tid <trigger-id>');
|
|
414
|
+
process.exit(1);
|
|
415
|
+
}
|
|
416
|
+
const data = await (0, _wixApi.wixRequest)({
|
|
417
|
+
path: `/_api/conversation-history/v1/conversations/by-trigger/${tid}`
|
|
418
|
+
});
|
|
419
|
+
printMessages(data.messages ?? [], opts.format ?? 'text');
|
|
420
|
+
} catch (err) {
|
|
421
|
+
console.error('Error:', err.message);
|
|
422
|
+
process.exit(1);
|
|
423
|
+
}
|
|
424
|
+
});
|
|
425
|
+
|
|
426
|
+
// ── list ───────────────────────────────────────────────────────────────────
|
|
427
|
+
|
|
428
|
+
const listCmd = new _commander.Command('list').description('List conversations (non-interactive)').option('--limit <n>', 'Maximum number of conversations to show', '50').option('--since <date>', 'Only show conversations created after this ISO date').action(async opts => {
|
|
429
|
+
const sp = (0, _ora.default)('Fetching conversations…').start();
|
|
430
|
+
try {
|
|
431
|
+
const data = await (0, _wixApi.wixRequest)({
|
|
432
|
+
path: '/web5/conversations/cli/roots/query',
|
|
433
|
+
method: 'POST',
|
|
434
|
+
body: {},
|
|
435
|
+
verbose
|
|
436
|
+
});
|
|
437
|
+
sp.stop();
|
|
438
|
+
let roots = data.messages ?? [];
|
|
439
|
+
if (opts.since) {
|
|
440
|
+
const since = new Date(opts.since).getTime();
|
|
441
|
+
if (isNaN(since)) {
|
|
442
|
+
console.error('Error: --since must be a valid ISO date string');
|
|
443
|
+
process.exit(1);
|
|
444
|
+
}
|
|
445
|
+
roots = roots.filter(r => {
|
|
446
|
+
if (!r.createdDate) return true;
|
|
447
|
+
return new Date(r.createdDate).getTime() >= since;
|
|
448
|
+
});
|
|
449
|
+
}
|
|
450
|
+
const limit = parseInt(opts.limit ?? '50', 10);
|
|
451
|
+
roots = roots.slice(0, limit);
|
|
452
|
+
if (roots.length === 0) {
|
|
453
|
+
console.log(_chalk.default.yellow('No conversations found.'));
|
|
454
|
+
return;
|
|
455
|
+
}
|
|
456
|
+
for (const r of roots) {
|
|
457
|
+
const label = truncate(r.triggerIdContent ?? r.text ?? r.content ?? '(no content)', 80);
|
|
458
|
+
const time = r.createdDate ? _chalk.default.dim(`[${new Date(r.createdDate).toLocaleString()}] `) : '';
|
|
459
|
+
const id = r.id ? _chalk.default.dim(` --id ${r.id}`) : '';
|
|
460
|
+
console.log(`${time}${label}${id}`);
|
|
461
|
+
}
|
|
462
|
+
} catch (err) {
|
|
463
|
+
sp.stop();
|
|
464
|
+
console.error('Error:', err.message);
|
|
465
|
+
process.exit(1);
|
|
466
|
+
}
|
|
467
|
+
});
|
|
468
|
+
|
|
469
|
+
// ── export ─────────────────────────────────────────────────────────────────
|
|
470
|
+
|
|
471
|
+
const exportCmd = new _commander.Command('export').description('Export a conversation to a file').requiredOption('--id <tid>', 'Trigger ID (TID) of the conversation').requiredOption('--output <file>', 'Output file path (.json or .md)').action(async opts => {
|
|
472
|
+
const sp = (0, _ora.default)(`Fetching conversation ${opts.id}…`).start();
|
|
473
|
+
try {
|
|
474
|
+
const data = await (0, _wixApi.wixRequest)({
|
|
475
|
+
path: `/_api/conversation-history/v1/conversations/by-trigger/${opts.id}`
|
|
476
|
+
});
|
|
477
|
+
sp.stop();
|
|
478
|
+
const outPath = path.resolve(opts.output);
|
|
479
|
+
const ext = path.extname(outPath).toLowerCase();
|
|
480
|
+
if (ext === '.md') {
|
|
481
|
+
const messages = data.messages ?? [];
|
|
482
|
+
const lines = [`# Conversation ${opts.id}`, ''];
|
|
483
|
+
for (const msg of messages) {
|
|
484
|
+
const role = msg.role === 'user' ? '**User**' : '**Assistant**';
|
|
485
|
+
const time = msg.createdDate ? ` _(${msg.createdDate})_` : '';
|
|
486
|
+
lines.push(`### ${role}${time}`, '', msg.content ?? '(empty)', '');
|
|
487
|
+
}
|
|
488
|
+
fs.writeFileSync(outPath, lines.join('\n'), 'utf8');
|
|
489
|
+
} else {
|
|
490
|
+
fs.writeFileSync(outPath, JSON.stringify(data, null, 2), 'utf8');
|
|
491
|
+
}
|
|
492
|
+
console.log(`Exported conversation to ${outPath}`);
|
|
493
|
+
} catch (err) {
|
|
494
|
+
sp.stop();
|
|
495
|
+
console.error('Error:', err.message);
|
|
496
|
+
process.exit(1);
|
|
497
|
+
}
|
|
498
|
+
});
|
|
499
|
+
|
|
500
|
+
// ── open ───────────────────────────────────────────────────────────────────
|
|
501
|
+
|
|
502
|
+
const openCmd = new _commander.Command('open').description('Open a conversation in the browser').requiredOption('--id <tid>', 'Trigger ID (TID) of the conversation').action(async opts => {
|
|
503
|
+
const browserUrl = `https://www.copyofcircanafordemo.com/web5#tid=${opts.id}`;
|
|
504
|
+
console.log(`Opening ${browserUrl}`);
|
|
505
|
+
await (0, _open.default)(browserUrl);
|
|
506
|
+
});
|
|
507
|
+
|
|
508
|
+
// ── Command export ─────────────────────────────────────────────────────────
|
|
509
|
+
|
|
510
|
+
const wizardCmd = new _commander.Command('wizard').description('Open the interactive TUI to browse conversation history').option('--logs', 'Print raw API requests and responses for debugging').action(async opts => {
|
|
511
|
+
try {
|
|
512
|
+
await runWizard(opts.logs ?? false);
|
|
513
|
+
} catch (err) {
|
|
514
|
+
const msg = err.message ?? '';
|
|
515
|
+
if (msg.includes('force closed') || msg.includes('User force')) {
|
|
516
|
+
console.log(_chalk.default.dim('\nBye.'));
|
|
517
|
+
process.exit(0);
|
|
518
|
+
}
|
|
519
|
+
console.error(_chalk.default.red('Unexpected error: ' + msg));
|
|
520
|
+
process.exit(1);
|
|
521
|
+
}
|
|
522
|
+
});
|
|
523
|
+
const conversationsCommand = exports.conversationsCommand = new _commander.Command('conversations').description('Conversation history').action(function () {
|
|
524
|
+
this.outputHelp();
|
|
525
|
+
}).addCommand(wizardCmd).addCommand(getCmd).addCommand(listCmd).addCommand(exportCmd).addCommand(openCmd);
|
|
526
|
+
//# sourceMappingURL=conversationWizard.js.map
|