@neetru/cli 2.12.5 → 2.12.7
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/commands/build.js +12 -7
- package/dist/commands/build.js.map +1 -1
- package/dist/commands/chat-menu.d.ts +10 -0
- package/dist/commands/chat-menu.js +563 -0
- package/dist/commands/chat-menu.js.map +1 -0
- package/dist/commands/chat.d.ts +64 -0
- package/dist/commands/chat.js +367 -0
- package/dist/commands/chat.js.map +1 -0
- package/dist/commands/db.d.ts +19 -0
- package/dist/commands/db.js +69 -0
- package/dist/commands/db.js.map +1 -1
- package/dist/commands/deploy.js +4 -1
- package/dist/commands/deploy.js.map +1 -1
- package/dist/commands/domains.d.ts +16 -0
- package/dist/commands/domains.js +211 -0
- package/dist/commands/domains.js.map +1 -0
- package/dist/commands/ui.d.ts +1 -1
- package/dist/commands/ui.js +41 -0
- package/dist/commands/ui.js.map +1 -1
- package/dist/index.js +50 -1
- package/dist/index.js.map +1 -1
- package/dist/lib/api-client.js +41 -20
- package/dist/lib/api-client.js.map +1 -1
- package/package.json +2 -2
|
@@ -0,0 +1,563 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Submenu de Chat — integrado ao menu interativo do CLI (`neetru` sem args).
|
|
3
|
+
*
|
|
4
|
+
* Exporta `runChatMenu()` que `ui.ts` chama quando o usuário seleciona "Chat"
|
|
5
|
+
* no menu principal.
|
|
6
|
+
*
|
|
7
|
+
* Fluxo:
|
|
8
|
+
* runChatMenu()
|
|
9
|
+
* └─ promptSubMenu "Chat"
|
|
10
|
+
* ├─ "Listar canais" → lista + seleciona → entrar no canal
|
|
11
|
+
* ├─ "Entrar em canal" → digita id ou escolhe → loop interativo
|
|
12
|
+
* ├─ "Abrir canal novo" → prompt nome/tipo → cria
|
|
13
|
+
* ├─ "Fechar canal" → prompt id → fecha (bloqueia 'global')
|
|
14
|
+
* └─ "Voltar"
|
|
15
|
+
*
|
|
16
|
+
* Loop interativo de canal (entrar em canal):
|
|
17
|
+
* - Exibe histórico das últimas 24h ao entrar.
|
|
18
|
+
* - readline pra enviar mensagem (Enter envia; linha em branco sai; Ctrl-C sai).
|
|
19
|
+
* - Ao sair volta pro submenu de chat.
|
|
20
|
+
*
|
|
21
|
+
* Ciclo de vida do stdin:
|
|
22
|
+
* - O `promptSubMenu` de `ui.ts` deixa o stdin "quente" (raw) antes de chamar
|
|
23
|
+
* `runChatMenu`. O loop interativo de canal usa `createInterface` (readline)
|
|
24
|
+
* que funciona sem raw mode. Antes de abrir o readline saímos do raw mode e
|
|
25
|
+
* restauramos ao terminar — padrão igual ao usado em `runChatLoop` de chat.ts.
|
|
26
|
+
* - `runChatMenu` NUNCA chama `process.exit` diretamente — a blindagem de
|
|
27
|
+
* `runTerminalUi` substitui `process.exit` por throw.
|
|
28
|
+
*/
|
|
29
|
+
import chalk from 'chalk';
|
|
30
|
+
import ora from 'ora';
|
|
31
|
+
import inquirer from 'inquirer';
|
|
32
|
+
import { createInterface } from 'node:readline';
|
|
33
|
+
import { apiRequest } from '../lib/api-client.js';
|
|
34
|
+
import { resolveToken } from '../lib/cli-read.js';
|
|
35
|
+
import { log } from '../utils/logger.js';
|
|
36
|
+
import { fmtTimestamp } from '../lib/render.js';
|
|
37
|
+
// ─── Helpers de display ───────────────────────────────────────────────────────
|
|
38
|
+
function channelTypeLabel(type) {
|
|
39
|
+
if (type === 'global')
|
|
40
|
+
return chalk.cyan('global');
|
|
41
|
+
if (type === 'product')
|
|
42
|
+
return chalk.blue('produto');
|
|
43
|
+
return chalk.dim('custom');
|
|
44
|
+
}
|
|
45
|
+
function channelTypeLabelPlain(type) {
|
|
46
|
+
if (type === 'global')
|
|
47
|
+
return 'global';
|
|
48
|
+
if (type === 'product')
|
|
49
|
+
return 'produto';
|
|
50
|
+
return 'custom';
|
|
51
|
+
}
|
|
52
|
+
/** Converte createdAt (Timestamp, string, number, ou unknown) em milissegundos. */
|
|
53
|
+
function toMillis(value) {
|
|
54
|
+
if (!value)
|
|
55
|
+
return 0;
|
|
56
|
+
if (typeof value === 'number')
|
|
57
|
+
return value;
|
|
58
|
+
if (typeof value === 'string')
|
|
59
|
+
return Date.parse(value) || 0;
|
|
60
|
+
// Firestore Timestamp-like: { seconds, nanoseconds }
|
|
61
|
+
if (typeof value === 'object' && value !== null) {
|
|
62
|
+
const obj = value;
|
|
63
|
+
if (typeof obj['seconds'] === 'number')
|
|
64
|
+
return obj['seconds'] * 1000;
|
|
65
|
+
if (typeof obj['_seconds'] === 'number')
|
|
66
|
+
return obj['_seconds'] * 1000;
|
|
67
|
+
// Instância com método toMillis()
|
|
68
|
+
if (typeof obj.toMillis === 'function') {
|
|
69
|
+
return obj.toMillis();
|
|
70
|
+
}
|
|
71
|
+
}
|
|
72
|
+
return 0;
|
|
73
|
+
}
|
|
74
|
+
/** Formata createdAt como HH:MM (hora local curta). */
|
|
75
|
+
function fmtHHMM(value) {
|
|
76
|
+
const ms = toMillis(value);
|
|
77
|
+
if (!ms)
|
|
78
|
+
return '--:--';
|
|
79
|
+
const d = new Date(ms);
|
|
80
|
+
return `${String(d.getHours()).padStart(2, '0')}:${String(d.getMinutes()).padStart(2, '0')}`;
|
|
81
|
+
}
|
|
82
|
+
function colorRole(role) {
|
|
83
|
+
if (role === 'operator')
|
|
84
|
+
return chalk.green('operador');
|
|
85
|
+
return chalk.cyan('dev');
|
|
86
|
+
}
|
|
87
|
+
function colorRoleSystem() {
|
|
88
|
+
return chalk.gray('sistema');
|
|
89
|
+
}
|
|
90
|
+
function actorLabel(msg) {
|
|
91
|
+
const email = msg.author?.email ?? msg.author?.actorId ?? '?';
|
|
92
|
+
const type = msg.author?.actorType ?? 'cli';
|
|
93
|
+
if (type === 'agent_claude')
|
|
94
|
+
return chalk.magenta(`[IA] ${email}`);
|
|
95
|
+
if (type === 'human') {
|
|
96
|
+
if (msg.role === 'operator')
|
|
97
|
+
return chalk.green(email);
|
|
98
|
+
return chalk.cyan(email);
|
|
99
|
+
}
|
|
100
|
+
// cli / sistema
|
|
101
|
+
return chalk.gray(`[cli] ${email}`);
|
|
102
|
+
}
|
|
103
|
+
/** Imprime uma mensagem individual com layout caprichado. */
|
|
104
|
+
function printMessage(msg) {
|
|
105
|
+
const ts = chalk.dim(fmtHHMM(msg.createdAt));
|
|
106
|
+
const type = msg.author?.actorType ?? 'cli';
|
|
107
|
+
const roleTag = type === 'agent_claude'
|
|
108
|
+
? colorRoleSystem()
|
|
109
|
+
: colorRole(msg.role);
|
|
110
|
+
const actor = actorLabel(msg);
|
|
111
|
+
// Linha de cabeçalho: timestamp + role + autor
|
|
112
|
+
process.stdout.write(`${ts} ${roleTag} ${actor}\n`);
|
|
113
|
+
// Corpo indentado
|
|
114
|
+
const lines = msg.body.split('\n');
|
|
115
|
+
for (const l of lines) {
|
|
116
|
+
process.stdout.write(` ${l}\n`);
|
|
117
|
+
}
|
|
118
|
+
process.stdout.write('\n');
|
|
119
|
+
}
|
|
120
|
+
function printChannel(ch) {
|
|
121
|
+
const tag = channelTypeLabel(ch.type);
|
|
122
|
+
const slug = ch.productSlug ? chalk.dim(` (${ch.productSlug})`) : '';
|
|
123
|
+
const lastMsg = ch.lastMessageAt
|
|
124
|
+
? chalk.dim(` última msg: ${fmtTimestamp(ch.lastMessageAt)}`)
|
|
125
|
+
: '';
|
|
126
|
+
console.log(` ${chalk.bold(ch.name)}${slug} ${tag} ${chalk.dim(ch.id)}${lastMsg}`);
|
|
127
|
+
}
|
|
128
|
+
// ─── API helpers ──────────────────────────────────────────────────────────────
|
|
129
|
+
async function fetchChannels(token) {
|
|
130
|
+
const res = await apiRequest('/api/cli/v1/chat/channels', { token });
|
|
131
|
+
return res.channels ?? [];
|
|
132
|
+
}
|
|
133
|
+
async function fetchMessages(token, channelId, sinceHours = 24) {
|
|
134
|
+
const qs = new URLSearchParams({ channelId, sinceHours: String(sinceHours) });
|
|
135
|
+
const res = await apiRequest(`/api/cli/v1/chat?${qs.toString()}`, { token });
|
|
136
|
+
return res.messages ?? [];
|
|
137
|
+
}
|
|
138
|
+
async function postMessage(token, channelId, text) {
|
|
139
|
+
const res = await apiRequest('/api/cli/v1/chat', {
|
|
140
|
+
method: 'POST',
|
|
141
|
+
token,
|
|
142
|
+
body: { channelId, message: text, actorType: 'cli' },
|
|
143
|
+
});
|
|
144
|
+
return res.id;
|
|
145
|
+
}
|
|
146
|
+
async function createChannel(token, name, type, productSlug) {
|
|
147
|
+
const res = await apiRequest('/api/cli/v1/chat/channels', {
|
|
148
|
+
method: 'POST',
|
|
149
|
+
token,
|
|
150
|
+
body: { name, type, ...(productSlug ? { productSlug } : {}) },
|
|
151
|
+
});
|
|
152
|
+
return res.id;
|
|
153
|
+
}
|
|
154
|
+
async function closeChannel(token, channelId) {
|
|
155
|
+
await apiRequest(`/api/cli/v1/chat/channels/${channelId}/close`, {
|
|
156
|
+
method: 'POST',
|
|
157
|
+
token,
|
|
158
|
+
body: {},
|
|
159
|
+
});
|
|
160
|
+
}
|
|
161
|
+
// ─── Loop interativo de canal ─────────────────────────────────────────────────
|
|
162
|
+
/** Largura da linha divisória ajustada ao terminal (máx 72). */
|
|
163
|
+
function divider(width = 72) {
|
|
164
|
+
const w = Math.min(width, process.stdout.columns ?? width);
|
|
165
|
+
return chalk.dim('─'.repeat(w));
|
|
166
|
+
}
|
|
167
|
+
/**
|
|
168
|
+
* Entra no loop de mensagens de um canal. Mostra histórico das últimas 24h,
|
|
169
|
+
* depois readline pra enviar mensagens. Linha em branco ou Ctrl-C volta pro
|
|
170
|
+
* menu de chat.
|
|
171
|
+
*
|
|
172
|
+
* Polling real-time: timer a cada ~2.5s busca mensagens novas (dedup por id).
|
|
173
|
+
* As mensagens novas são impressas ACIMA do prompt readline (re-escrevendo a
|
|
174
|
+
* linha de input) de forma não-intrusiva. Timer é limpo no cleanup.
|
|
175
|
+
*
|
|
176
|
+
* Gerencia raw mode: desativa raw ao entrar (readline precisa de modo canônico)
|
|
177
|
+
* e restaura ao sair.
|
|
178
|
+
*/
|
|
179
|
+
async function runChannelLoop(token, channel) {
|
|
180
|
+
const POLL_INTERVAL_MS = 2500;
|
|
181
|
+
// Sai do raw mode pra readline funcionar corretamente
|
|
182
|
+
const wasRaw = process.stdin.isRaw === true;
|
|
183
|
+
if (typeof process.stdin.setRawMode === 'function') {
|
|
184
|
+
process.stdin.setRawMode(false);
|
|
185
|
+
}
|
|
186
|
+
process.stdout.write('\x1B[?25h'); // mostra cursor
|
|
187
|
+
let pollTimer = null;
|
|
188
|
+
try {
|
|
189
|
+
// ── Limpa a tela e imprime o header do canal ──────────────────────────
|
|
190
|
+
process.stdout.write('\x1B[2J\x1B[H'); // clear screen, cursor ao topo
|
|
191
|
+
const typeLabel = channelTypeLabelPlain(channel.type);
|
|
192
|
+
const headerLine = ` ${chalk.bold.cyan(channel.name)}` +
|
|
193
|
+
` ${chalk.dim(`[${typeLabel}]`)}` +
|
|
194
|
+
(channel.productSlug ? chalk.dim(` produto: ${channel.productSlug}`) : '') +
|
|
195
|
+
` ${chalk.dim(channel.id)}`;
|
|
196
|
+
process.stdout.write(`\n${divider()}\n`);
|
|
197
|
+
process.stdout.write(`${headerLine}\n`);
|
|
198
|
+
process.stdout.write(`${divider()}\n`);
|
|
199
|
+
process.stdout.write(chalk.dim(' Ctrl-C ou linha em branco para sair · mensagens novas aparecem automaticamente\n'));
|
|
200
|
+
process.stdout.write(`${divider()}\n\n`);
|
|
201
|
+
// ── Carrega histórico das últimas 24h ─────────────────────────────────
|
|
202
|
+
const spinner = ora({ text: 'Carregando histórico…', color: 'cyan' }).start();
|
|
203
|
+
let messages = [];
|
|
204
|
+
try {
|
|
205
|
+
messages = await fetchMessages(token, channel.id);
|
|
206
|
+
spinner.stop();
|
|
207
|
+
}
|
|
208
|
+
catch {
|
|
209
|
+
spinner.fail('Falha ao carregar histórico — continuando sem ele.');
|
|
210
|
+
}
|
|
211
|
+
// Conjunto de IDs já vistos (dedup do polling)
|
|
212
|
+
const seenIds = new Set(messages.map((m) => m.id));
|
|
213
|
+
if (messages.length > 0) {
|
|
214
|
+
process.stdout.write(chalk.dim(` Últimas 24h — ${messages.length} mensagem(ns):\n\n`));
|
|
215
|
+
for (const msg of messages)
|
|
216
|
+
printMessage(msg);
|
|
217
|
+
}
|
|
218
|
+
else {
|
|
219
|
+
process.stdout.write(chalk.dim(' Nenhuma mensagem nas últimas 24h.\n\n'));
|
|
220
|
+
}
|
|
221
|
+
if (!process.stdin.isTTY) {
|
|
222
|
+
log.error('Terminal não-interativo — não é possível enviar mensagens aqui.');
|
|
223
|
+
return;
|
|
224
|
+
}
|
|
225
|
+
// ── Readline de input ─────────────────────────────────────────────────
|
|
226
|
+
const rl = createInterface({ input: process.stdin, output: process.stdout });
|
|
227
|
+
/**
|
|
228
|
+
* Imprime mensagens novas sem quebrar o prompt do readline.
|
|
229
|
+
* Estratégia: apaga a linha do prompt atual (ANSI), imprime as msgs,
|
|
230
|
+
* depois re-escreve o prompt. Degradação graciosa em terminais sem ANSI.
|
|
231
|
+
*/
|
|
232
|
+
const printNewMessages = (newMsgs) => {
|
|
233
|
+
if (newMsgs.length === 0)
|
|
234
|
+
return;
|
|
235
|
+
// Apaga a linha do prompt atual
|
|
236
|
+
process.stdout.write('\r\x1B[K');
|
|
237
|
+
for (const msg of newMsgs)
|
|
238
|
+
printMessage(msg);
|
|
239
|
+
// Re-escreve o prompt manualmente (readline não tem API pública pra isso)
|
|
240
|
+
process.stdout.write(chalk.cyan('> '));
|
|
241
|
+
};
|
|
242
|
+
// ── Timer de polling ──────────────────────────────────────────────────
|
|
243
|
+
let pollActive = true;
|
|
244
|
+
pollTimer = setInterval(() => {
|
|
245
|
+
if (!pollActive)
|
|
246
|
+
return;
|
|
247
|
+
fetchMessages(token, channel.id)
|
|
248
|
+
.then((all) => {
|
|
249
|
+
if (!pollActive)
|
|
250
|
+
return;
|
|
251
|
+
const newMsgs = all.filter((m) => !seenIds.has(m.id));
|
|
252
|
+
if (newMsgs.length > 0) {
|
|
253
|
+
// Ordena por createdAt antes de exibir
|
|
254
|
+
newMsgs.sort((a, b) => toMillis(a.createdAt) - toMillis(b.createdAt));
|
|
255
|
+
for (const m of newMsgs)
|
|
256
|
+
seenIds.add(m.id);
|
|
257
|
+
printNewMessages(newMsgs);
|
|
258
|
+
}
|
|
259
|
+
})
|
|
260
|
+
.catch(() => {
|
|
261
|
+
// Silencia erros de polling — não interrompe o uso
|
|
262
|
+
});
|
|
263
|
+
}, POLL_INTERVAL_MS);
|
|
264
|
+
// ── Loop de input ─────────────────────────────────────────────────────
|
|
265
|
+
const askLine = () => new Promise((resolve) => {
|
|
266
|
+
rl.question(chalk.cyan('> '), (answer) => resolve(answer.trim()));
|
|
267
|
+
});
|
|
268
|
+
// eslint-disable-next-line no-constant-condition
|
|
269
|
+
while (true) {
|
|
270
|
+
let line;
|
|
271
|
+
try {
|
|
272
|
+
line = await askLine();
|
|
273
|
+
}
|
|
274
|
+
catch {
|
|
275
|
+
// Ctrl-C ou fechamento do stream
|
|
276
|
+
break;
|
|
277
|
+
}
|
|
278
|
+
if (!line)
|
|
279
|
+
break;
|
|
280
|
+
const sendSpinner = ora({ text: 'Enviando…', color: 'cyan' }).start();
|
|
281
|
+
try {
|
|
282
|
+
const id = await postMessage(token, channel.id, line);
|
|
283
|
+
sendSpinner.stop();
|
|
284
|
+
// Adiciona o id ao seenIds para o polling não reexibir a própria msg
|
|
285
|
+
seenIds.add(id);
|
|
286
|
+
// Confirmação discreta inline
|
|
287
|
+
process.stdout.write(chalk.dim(` ✓ enviado\n\n`));
|
|
288
|
+
}
|
|
289
|
+
catch (error) {
|
|
290
|
+
sendSpinner.fail('Falha ao enviar.');
|
|
291
|
+
if (error instanceof Error) {
|
|
292
|
+
process.stdout.write(chalk.red(` ${error.message}\n`));
|
|
293
|
+
}
|
|
294
|
+
// Não encerra o loop — permite tentar de novo
|
|
295
|
+
}
|
|
296
|
+
}
|
|
297
|
+
pollActive = false;
|
|
298
|
+
rl.close();
|
|
299
|
+
process.stdout.write(chalk.dim('\n (Saindo do canal…)\n\n'));
|
|
300
|
+
}
|
|
301
|
+
finally {
|
|
302
|
+
// Para o timer de polling
|
|
303
|
+
if (pollTimer !== null) {
|
|
304
|
+
clearInterval(pollTimer);
|
|
305
|
+
pollTimer = null;
|
|
306
|
+
}
|
|
307
|
+
// Restaura raw mode pro menu retomar corretamente
|
|
308
|
+
if (typeof process.stdin.setRawMode === 'function') {
|
|
309
|
+
process.stdin.setRawMode(wasRaw);
|
|
310
|
+
}
|
|
311
|
+
process.stdin.resume();
|
|
312
|
+
}
|
|
313
|
+
}
|
|
314
|
+
// ─── Submenu: listar canais e selecionar ─────────────────────────────────────
|
|
315
|
+
/**
|
|
316
|
+
* Lista canais, exibe tabela, e oferece seleção via inquirer (modo não-raw).
|
|
317
|
+
* Retorna o canal selecionado ou `null` se o usuário cancelou.
|
|
318
|
+
*/
|
|
319
|
+
async function promptSelectChannel(token, channels) {
|
|
320
|
+
if (channels.length === 0) {
|
|
321
|
+
log.dim('Nenhum canal aberto encontrado.');
|
|
322
|
+
return null;
|
|
323
|
+
}
|
|
324
|
+
console.log();
|
|
325
|
+
console.log(chalk.bold('Canais disponíveis:\n'));
|
|
326
|
+
for (const ch of channels)
|
|
327
|
+
printChannel(ch);
|
|
328
|
+
console.log();
|
|
329
|
+
const choices = [
|
|
330
|
+
...channels.map((ch) => ({
|
|
331
|
+
name: `${chalk.bold(ch.name)} ${channelTypeLabel(ch.type)} ${chalk.dim(ch.id)}`,
|
|
332
|
+
value: ch.id,
|
|
333
|
+
short: ch.name,
|
|
334
|
+
})),
|
|
335
|
+
{ name: chalk.dim('Cancelar'), value: '__cancel__', short: 'Cancelar' },
|
|
336
|
+
];
|
|
337
|
+
const { selected } = await inquirer.prompt([
|
|
338
|
+
{
|
|
339
|
+
type: 'list',
|
|
340
|
+
name: 'selected',
|
|
341
|
+
message: 'Selecione um canal:',
|
|
342
|
+
choices,
|
|
343
|
+
},
|
|
344
|
+
]);
|
|
345
|
+
if (selected === '__cancel__')
|
|
346
|
+
return null;
|
|
347
|
+
return channels.find((ch) => ch.id === selected) ?? null;
|
|
348
|
+
}
|
|
349
|
+
// ─── Submenu: criar canal ─────────────────────────────────────────────────────
|
|
350
|
+
async function promptCreateChannel(token) {
|
|
351
|
+
const { name, type } = await inquirer.prompt([
|
|
352
|
+
{
|
|
353
|
+
type: 'input',
|
|
354
|
+
name: 'name',
|
|
355
|
+
message: 'Nome do canal:',
|
|
356
|
+
validate: (v) => v.trim().length > 0 || 'Obrigatório.',
|
|
357
|
+
},
|
|
358
|
+
{
|
|
359
|
+
type: 'list',
|
|
360
|
+
name: 'type',
|
|
361
|
+
message: 'Tipo do canal:',
|
|
362
|
+
choices: [
|
|
363
|
+
{ name: 'Produto (vinculado a um produto Neetru)', value: 'product', short: 'produto' },
|
|
364
|
+
{ name: 'Geral (sem produto específico)', value: 'custom', short: 'geral' },
|
|
365
|
+
],
|
|
366
|
+
},
|
|
367
|
+
]);
|
|
368
|
+
let productSlug;
|
|
369
|
+
if (type === 'product') {
|
|
370
|
+
const ans = await inquirer.prompt([
|
|
371
|
+
{
|
|
372
|
+
type: 'input',
|
|
373
|
+
name: 'slug',
|
|
374
|
+
message: 'Slug do produto (ex: pdv-agiliza):',
|
|
375
|
+
validate: (v) => v.trim().length > 0 || 'Obrigatório.',
|
|
376
|
+
},
|
|
377
|
+
]);
|
|
378
|
+
productSlug = ans.slug.trim();
|
|
379
|
+
}
|
|
380
|
+
const spinner = ora({ text: 'Criando canal…', color: 'blue' }).start();
|
|
381
|
+
try {
|
|
382
|
+
const id = await createChannel(token, name.trim(), type, productSlug);
|
|
383
|
+
spinner.stop();
|
|
384
|
+
log.success(`Canal criado com sucesso (id: ${id})`);
|
|
385
|
+
}
|
|
386
|
+
catch (error) {
|
|
387
|
+
spinner.fail('Falha ao criar canal.');
|
|
388
|
+
if (error instanceof Error)
|
|
389
|
+
console.error(chalk.red(` ${error.message}`));
|
|
390
|
+
}
|
|
391
|
+
}
|
|
392
|
+
// ─── Submenu: fechar canal ────────────────────────────────────────────────────
|
|
393
|
+
async function promptCloseChannel(token, channels) {
|
|
394
|
+
const closeable = channels.filter((ch) => ch.id !== 'global');
|
|
395
|
+
if (closeable.length === 0) {
|
|
396
|
+
log.dim('Nenhum canal disponível para fechar (o canal Global nunca pode ser fechado).');
|
|
397
|
+
return;
|
|
398
|
+
}
|
|
399
|
+
const choices = [
|
|
400
|
+
...closeable.map((ch) => ({
|
|
401
|
+
name: `${chalk.bold(ch.name)} ${channelTypeLabel(ch.type)} ${chalk.dim(ch.id)}`,
|
|
402
|
+
value: ch.id,
|
|
403
|
+
short: ch.name,
|
|
404
|
+
})),
|
|
405
|
+
{ name: chalk.dim('Cancelar'), value: '__cancel__', short: 'Cancelar' },
|
|
406
|
+
];
|
|
407
|
+
const { channelId } = await inquirer.prompt([
|
|
408
|
+
{
|
|
409
|
+
type: 'list',
|
|
410
|
+
name: 'channelId',
|
|
411
|
+
message: 'Qual canal fechar?',
|
|
412
|
+
choices,
|
|
413
|
+
},
|
|
414
|
+
]);
|
|
415
|
+
if (channelId === '__cancel__')
|
|
416
|
+
return;
|
|
417
|
+
const { confirm } = await inquirer.prompt([
|
|
418
|
+
{
|
|
419
|
+
type: 'confirm',
|
|
420
|
+
name: 'confirm',
|
|
421
|
+
message: `Confirma fechar o canal "${closeable.find((c) => c.id === channelId)?.name ?? channelId}"?`,
|
|
422
|
+
default: false,
|
|
423
|
+
},
|
|
424
|
+
]);
|
|
425
|
+
if (!confirm) {
|
|
426
|
+
log.dim('Operação cancelada.');
|
|
427
|
+
return;
|
|
428
|
+
}
|
|
429
|
+
const spinner = ora({ text: 'Fechando canal…', color: 'blue' }).start();
|
|
430
|
+
try {
|
|
431
|
+
await closeChannel(token, channelId);
|
|
432
|
+
spinner.stop();
|
|
433
|
+
log.success('Canal fechado.');
|
|
434
|
+
}
|
|
435
|
+
catch (error) {
|
|
436
|
+
spinner.fail('Falha ao fechar canal.');
|
|
437
|
+
if (error instanceof Error)
|
|
438
|
+
console.error(chalk.red(` ${error.message}`));
|
|
439
|
+
}
|
|
440
|
+
}
|
|
441
|
+
// ─── Entrada principal do submenu de chat ─────────────────────────────────────
|
|
442
|
+
/**
|
|
443
|
+
* Submenu raiz de Chat. Chamado por `runTerminalUi` em `ui.ts`.
|
|
444
|
+
*
|
|
445
|
+
* Usa o `promptSubMenu` de `ui.ts` indiretamente por reimplementação local
|
|
446
|
+
* que delega ao `inquirer` list (mode não-raw) — compatível com o ciclo de
|
|
447
|
+
* vida do menu principal, que passa o controle com stdin "quente".
|
|
448
|
+
*
|
|
449
|
+
* O loop `for (;;)` mantém o submenu ativo até o usuário escolher "Voltar".
|
|
450
|
+
*/
|
|
451
|
+
export async function runChatMenu() {
|
|
452
|
+
const token = await resolveToken();
|
|
453
|
+
if (!token) {
|
|
454
|
+
log.error('Sessão não encontrada. Faça login com `neetru login`.');
|
|
455
|
+
return;
|
|
456
|
+
}
|
|
457
|
+
for (;;) {
|
|
458
|
+
// Carrega canais pra ter a lista disponível nas ações que precisam
|
|
459
|
+
let channels = [];
|
|
460
|
+
try {
|
|
461
|
+
const spinner = ora({ text: 'Carregando canais…', color: 'blue' }).start();
|
|
462
|
+
channels = await fetchChannels(token);
|
|
463
|
+
spinner.stop();
|
|
464
|
+
}
|
|
465
|
+
catch {
|
|
466
|
+
// Continua mesmo sem lista — algumas ações ainda funcionam
|
|
467
|
+
}
|
|
468
|
+
// Resumo rápido no topo do submenu
|
|
469
|
+
console.log();
|
|
470
|
+
if (channels.length > 0) {
|
|
471
|
+
const globalCh = channels.find((c) => c.id === 'global');
|
|
472
|
+
console.log(chalk.bold('Chat — canais abertos: ') +
|
|
473
|
+
chalk.cyan(String(channels.length)) +
|
|
474
|
+
(globalCh ? chalk.dim(' (global disponível)') : ''));
|
|
475
|
+
}
|
|
476
|
+
else {
|
|
477
|
+
console.log(chalk.bold('Chat'));
|
|
478
|
+
}
|
|
479
|
+
console.log();
|
|
480
|
+
const { action } = await inquirer.prompt([
|
|
481
|
+
{
|
|
482
|
+
type: 'list',
|
|
483
|
+
name: 'action',
|
|
484
|
+
message: 'Chat — o que deseja fazer?',
|
|
485
|
+
choices: [
|
|
486
|
+
{
|
|
487
|
+
name: `${chalk.bold('Listar canais')} ${chalk.dim('— ver lista e entrar num canal')}`,
|
|
488
|
+
value: 'list',
|
|
489
|
+
short: 'Listar canais',
|
|
490
|
+
},
|
|
491
|
+
{
|
|
492
|
+
name: `${chalk.bold('Entrar em canal')} ${chalk.dim('— digitar id ou escolher')}`,
|
|
493
|
+
value: 'enter',
|
|
494
|
+
short: 'Entrar em canal',
|
|
495
|
+
},
|
|
496
|
+
{
|
|
497
|
+
name: `${chalk.bold('Abrir canal novo')} ${chalk.dim('— criar canal de produto ou geral')}`,
|
|
498
|
+
value: 'new',
|
|
499
|
+
short: 'Abrir canal novo',
|
|
500
|
+
},
|
|
501
|
+
{
|
|
502
|
+
name: `${chalk.bold('Fechar canal')} ${chalk.dim('— marcar canal como encerrado')}`,
|
|
503
|
+
value: 'close',
|
|
504
|
+
short: 'Fechar canal',
|
|
505
|
+
},
|
|
506
|
+
{
|
|
507
|
+
name: chalk.dim('Voltar'),
|
|
508
|
+
value: 'back',
|
|
509
|
+
short: 'Voltar',
|
|
510
|
+
},
|
|
511
|
+
],
|
|
512
|
+
},
|
|
513
|
+
]);
|
|
514
|
+
if (action === 'back')
|
|
515
|
+
return;
|
|
516
|
+
if (action === 'list') {
|
|
517
|
+
if (channels.length === 0) {
|
|
518
|
+
log.dim('Nenhum canal aberto. Use "Abrir canal novo" pra criar um.');
|
|
519
|
+
continue;
|
|
520
|
+
}
|
|
521
|
+
const selected = await promptSelectChannel(token, channels);
|
|
522
|
+
if (selected) {
|
|
523
|
+
await runChannelLoop(token, selected);
|
|
524
|
+
}
|
|
525
|
+
continue;
|
|
526
|
+
}
|
|
527
|
+
if (action === 'enter') {
|
|
528
|
+
if (channels.length > 0) {
|
|
529
|
+
// Oferece seleção visual quando há canais disponíveis
|
|
530
|
+
const selected = await promptSelectChannel(token, channels);
|
|
531
|
+
if (selected) {
|
|
532
|
+
await runChannelLoop(token, selected);
|
|
533
|
+
}
|
|
534
|
+
}
|
|
535
|
+
else {
|
|
536
|
+
// Sem canais: pede o id manualmente
|
|
537
|
+
const { channelId } = await inquirer.prompt([
|
|
538
|
+
{
|
|
539
|
+
type: 'input',
|
|
540
|
+
name: 'channelId',
|
|
541
|
+
message: 'ID do canal (ex: global):',
|
|
542
|
+
validate: (v) => v.trim().length > 0 || 'Obrigatório.',
|
|
543
|
+
},
|
|
544
|
+
]);
|
|
545
|
+
const id = channelId.trim();
|
|
546
|
+
// Canal sintético com mínimo de info pra entrar no loop
|
|
547
|
+
const synthetic = { id, name: id, type: 'custom' };
|
|
548
|
+
await runChannelLoop(token, synthetic);
|
|
549
|
+
}
|
|
550
|
+
continue;
|
|
551
|
+
}
|
|
552
|
+
if (action === 'new') {
|
|
553
|
+
await promptCreateChannel(token);
|
|
554
|
+
// Depois de criar, volta ao loop pra atualizar a lista
|
|
555
|
+
continue;
|
|
556
|
+
}
|
|
557
|
+
if (action === 'close') {
|
|
558
|
+
await promptCloseChannel(token, channels);
|
|
559
|
+
continue;
|
|
560
|
+
}
|
|
561
|
+
}
|
|
562
|
+
}
|
|
563
|
+
//# sourceMappingURL=chat-menu.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"chat-menu.js","sourceRoot":"","sources":["../../src/commands/chat-menu.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,64 @@
|
|
|
1
|
+
import type { Command } from 'commander';
|
|
2
|
+
type ActorType = 'agent_claude' | 'human' | 'cli';
|
|
3
|
+
export interface ChatChannelsOptions {
|
|
4
|
+
json?: boolean;
|
|
5
|
+
}
|
|
6
|
+
/**
|
|
7
|
+
* Lista os canais de chat abertos.
|
|
8
|
+
*
|
|
9
|
+
* integrationNeeded — registrar em `registerChatCommand`:
|
|
10
|
+
* ```ts
|
|
11
|
+
* chatCmd.command('channels').action(async (opts) => runChatChannels(opts));
|
|
12
|
+
* ```
|
|
13
|
+
*/
|
|
14
|
+
export declare function runChatChannels(opts: ChatChannelsOptions): Promise<void>;
|
|
15
|
+
export interface ChatSendOptions {
|
|
16
|
+
/** Canal de destino (novo — tem precedência sobre product). */
|
|
17
|
+
channel?: string;
|
|
18
|
+
/** Produto legado (mantido por retrocompat; ignorado quando channel está presente). */
|
|
19
|
+
product?: string;
|
|
20
|
+
actorType?: ActorType;
|
|
21
|
+
productId?: string;
|
|
22
|
+
json?: boolean;
|
|
23
|
+
}
|
|
24
|
+
export declare function runChatSend(message: string, opts: ChatSendOptions): Promise<void>;
|
|
25
|
+
export interface ChatHistoryOptions {
|
|
26
|
+
/** Canal de destino (novo — tem precedência sobre product). */
|
|
27
|
+
channel?: string;
|
|
28
|
+
/** Produto legado (mantido por retrocompat). */
|
|
29
|
+
product?: string;
|
|
30
|
+
hours?: string;
|
|
31
|
+
json?: boolean;
|
|
32
|
+
}
|
|
33
|
+
export declare function runChatHistory(opts: ChatHistoryOptions): Promise<void>;
|
|
34
|
+
export interface ChatLoopOptions {
|
|
35
|
+
/** Canal de destino (novo — tem precedência sobre product). */
|
|
36
|
+
channel?: string;
|
|
37
|
+
/** Produto legado (retrocompat). */
|
|
38
|
+
product?: string;
|
|
39
|
+
actorType?: ActorType;
|
|
40
|
+
json?: boolean;
|
|
41
|
+
}
|
|
42
|
+
export declare function runChatLoop(opts: ChatLoopOptions): Promise<void>;
|
|
43
|
+
/**
|
|
44
|
+
* Registra o comando `neetru chat` no programa Commander.
|
|
45
|
+
*
|
|
46
|
+
* Subcomandos:
|
|
47
|
+
* neetru chat channels → lista canais abertos
|
|
48
|
+
* neetru chat send --channel <id> "msg" → envia mensagem num canal
|
|
49
|
+
* neetru chat send --product <slug> "msg" → legado (por produto)
|
|
50
|
+
* neetru chat history --channel <id> → histórico de canal
|
|
51
|
+
* neetru chat history --product <slug> → histórico legado
|
|
52
|
+
* neetru chat --channel <id> → loop interativo de canal
|
|
53
|
+
* neetru chat --product <slug> → loop interativo legado
|
|
54
|
+
*
|
|
55
|
+
* integrationNeeded — adicionar em src/index.ts (ou onde os subcomandos
|
|
56
|
+
* são registrados):
|
|
57
|
+
* ```ts
|
|
58
|
+
* import { registerChatCommand } from './commands/chat.js';
|
|
59
|
+
* // ...
|
|
60
|
+
* registerChatCommand(program);
|
|
61
|
+
* ```
|
|
62
|
+
*/
|
|
63
|
+
export declare function registerChatCommand(program: Command): void;
|
|
64
|
+
export {};
|