chocolatito-code 1.6.6 → 1.6.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/index.js +65 -33
- package/dist/ui/ink/App.d.ts +0 -23
- package/dist/ui/ink/App.js +86 -57
- package/dist/ui/ink/Prompt.d.ts +16 -6
- package/dist/ui/ink/Prompt.js +37 -62
- package/dist/ui/ink/montarApp.d.ts +34 -0
- package/dist/ui/ink/montarApp.js +93 -1
- package/dist/ui/ink/prestamo.d.ts +63 -0
- package/dist/ui/ink/prestamo.js +92 -0
- package/dist/ui/ink/teclado.d.ts +48 -0
- package/dist/ui/ink/teclado.js +96 -0
- package/dist/ui/ink/transcripcion.d.ts +114 -0
- package/dist/ui/ink/transcripcion.js +180 -0
- package/dist/ui/interrupt.js +4 -1
- package/dist/ui/loopPrompt.d.ts +6 -7
- package/dist/ui/loopPrompt.js +14 -1
- package/dist/ui/marco.d.ts +2 -0
- package/dist/ui/marco.js +18 -1
- package/dist/ui/pantalla.d.ts +45 -17
- package/dist/ui/pantalla.js +150 -92
- package/dist/ui/permissionPrompt.d.ts +10 -17
- package/dist/ui/permissionPrompt.js +14 -1
- package/dist/ui/pieFijo.js +26 -4
- package/dist/ui/selector.d.ts +6 -4
- package/dist/ui/selector.js +14 -1
- package/extension/manifest.json +60 -60
- package/package.json +1 -1
- package/dist/ui/historial.d.ts +0 -49
- package/dist/ui/historial.js +0 -92
package/dist/ui/pantalla.js
CHANGED
|
@@ -1,139 +1,197 @@
|
|
|
1
1
|
import process from "node:process";
|
|
2
|
-
import
|
|
3
|
-
import os from "node:os";
|
|
4
|
-
import path from "node:path";
|
|
2
|
+
import { format } from "node:util";
|
|
5
3
|
import { redirigirDibujo } from "./salida.js";
|
|
6
|
-
import {
|
|
4
|
+
import { anotar } from "./ink/transcripcion.js";
|
|
7
5
|
import { habilitarPie } from "./pieFijo.js";
|
|
6
|
+
import { limpiarLaPantalla } from "./ink/montarApp.js";
|
|
8
7
|
/**
|
|
9
|
-
* LA PANTALLA
|
|
8
|
+
* QUIÉN ES DUEÑO DE LA PANTALLA
|
|
10
9
|
*
|
|
11
|
-
*
|
|
12
|
-
* terminal, no una capa encima. Ninguna secuencia de escape la clava ahí; lo
|
|
13
|
-
* único que lo consigue es que el programa tome la pantalla entera, como hacen
|
|
14
|
-
* vim o htop.
|
|
10
|
+
* LO QUE HABÍA AQUÍ ANTES, Y POR QUÉ SE FUE
|
|
15
11
|
*
|
|
16
|
-
*
|
|
12
|
+
* Este archivo tomaba la pantalla alternativa —la de vim o htop— para clavar la
|
|
13
|
+
* barra de abajo. Es la única forma de clavarla de verdad, y se pidió cinco
|
|
14
|
+
* veces, así que se hizo. Se publicó rota dos veces: "no sale nada, se bugea" y
|
|
15
|
+
* "sale una barra y lo demás negro, escribo y se cierra".
|
|
17
16
|
*
|
|
18
|
-
*
|
|
19
|
-
*
|
|
20
|
-
*
|
|
17
|
+
* Y resultó que además era la arquitectura equivocada. Claude Code, que era el
|
|
18
|
+
* ejemplo a copiar, NO usa la pantalla alternativa: renderiza en el buffer
|
|
19
|
+
* normal y emite la conversación con `<Static>` de Ink, que la escribe una vez y
|
|
20
|
+
* la deja en el historial del terminal. Por eso allí la rueda del ratón funciona.
|
|
21
|
+
* Y por eso allí la barra tampoco se queda quieta si subes: se va con el resto.
|
|
21
22
|
*
|
|
22
|
-
*
|
|
23
|
-
* el conducto de dibujo: media docena de sitios —el arranque, la licencia, los
|
|
24
|
-
* avisos— siguen imprimiendo directo, y en la pantalla alternativa eso escribe
|
|
25
|
-
* encima de lo que Ink acaba de dibujar y descuadra el árbol entero.
|
|
23
|
+
* QUÉ HACE AHORA
|
|
26
24
|
*
|
|
27
|
-
*
|
|
25
|
+
* Enciende el modo de árbol único: un solo componente de Ink vivo toda la
|
|
26
|
+
* sesión, en la pantalla de siempre. Lo que cambia respecto al modo clásico:
|
|
28
27
|
*
|
|
29
|
-
*
|
|
30
|
-
*
|
|
31
|
-
*
|
|
32
|
-
*
|
|
28
|
+
* - El dibujo del agente deja de ir al terminal y entra en la transcripción,
|
|
29
|
+
* que es lo que `<Static>` va escribiendo (ink/transcripcion.ts).
|
|
30
|
+
* - `pieFijo` deja de pintar. Sigue guardando el spinner y la línea de
|
|
31
|
+
* razonamiento, pero quien los dibuja pasa a ser el árbol. Dos dueños del
|
|
32
|
+
* mismo trozo de pantalla es el problema que esto viene a quitar.
|
|
33
|
+
*
|
|
34
|
+
* Y SE SIGUE INTERCEPTANDO `console`, PERO POR OTRO MOTIVO
|
|
35
|
+
*
|
|
36
|
+
* Ink trae su propio `patchConsole`, y hace lo correcto: borra su marco, escribe
|
|
37
|
+
* el mensaje y repinta debajo. Aquí no se usa, y no es por desconfianza: es por
|
|
38
|
+
* el ORDEN.
|
|
39
|
+
*
|
|
40
|
+
* Lo que escribe el agente entra en la transcripción y sale cuando React confirma
|
|
41
|
+
* el dibujado. Un `console.log` con el parche de Ink sale en el acto. Dos caminos
|
|
42
|
+
* con tiempos distintos para el mismo hilo de conversación, y entonces el aviso
|
|
43
|
+
* de un hook puede aparecer por encima de la frase que lo provocó. Es de los
|
|
44
|
+
* fallos que no se notan hasta que confundes a alguien.
|
|
45
|
+
*
|
|
46
|
+
* Mandando los dos por la transcripción hay una sola cola y el orden es el de
|
|
47
|
+
* verdad. Se cubren `log`, `error`, `warn` e `info` —el parche de antes solo
|
|
48
|
+
* cubría `log`— y se formatea con `util.format`, que es lo que hace `console` de
|
|
49
|
+
* serie: sin eso, un `console.log("%s pruebas", 12)` sale con el `%s` puesto.
|
|
33
50
|
*/
|
|
34
|
-
const ENTRAR = "\x1b[?1049h";
|
|
35
|
-
const SALIR = "\x1b[?1049l";
|
|
36
51
|
let dentro = false;
|
|
37
|
-
|
|
52
|
+
const original = {};
|
|
38
53
|
/**
|
|
39
|
-
*
|
|
54
|
+
* De serie SÍ, desde la 1.6.7, y con salida de emergencia.
|
|
55
|
+
*
|
|
56
|
+
* DOS VECES ESTUVO AQUÍ Y DOS VECES SALIÓ ROTO
|
|
40
57
|
*
|
|
41
|
-
* La
|
|
58
|
+
* La 1.6.0 salió en negro ("no sale nada, se bugea") y la 1.6.5 con "una barra y
|
|
59
|
+
* lo demás negro, escribo y se cierra". Las dos veces pasaban las 820 pruebas:
|
|
60
|
+
* un emulador prueba lo que sabe emular, y una consola de verdad hace cosas que
|
|
61
|
+
* no sabe.
|
|
42
62
|
*
|
|
43
|
-
*
|
|
44
|
-
*
|
|
45
|
-
*
|
|
46
|
-
*
|
|
47
|
-
*
|
|
63
|
+
* Esta vez el orden fue el otro: se entregó detrás de la variable, el dueño lo
|
|
64
|
+
* corrió en SU consola, y solo después pasó a ser lo normal. Lo hizo, y lo
|
|
65
|
+
* aprobó sabiendo lo que no le iba a gustar: que la caja no se queda clavada al
|
|
66
|
+
* hacer scroll. No se queda porque es texto del terminal, y en Claude Code
|
|
67
|
+
* tampoco se queda. Es el precio de recuperar la rueda del ratón y el historial.
|
|
68
|
+
*
|
|
69
|
+
* CHOCOLATITO_PANTALLA=normal devuelve la interfaz clásica. Existe porque una
|
|
70
|
+
* consola rara —una que no sea la suya ni la mía— puede seguir haciendo algo que
|
|
71
|
+
* no habíamos visto, y entonces el usuario necesita poder trabajar hoy, no
|
|
72
|
+
* esperar al parche.
|
|
48
73
|
*/
|
|
49
74
|
export function pantallaFijaPedida() {
|
|
50
|
-
return process.env.CHOCOLATITO_PANTALLA
|
|
75
|
+
return process.env.CHOCOLATITO_PANTALLA !== "normal";
|
|
51
76
|
}
|
|
52
77
|
/** `null` = manda el estado real. Las pruebas lo fuerzan. */
|
|
53
78
|
let forzado = null;
|
|
54
|
-
/**
|
|
55
|
-
* Enciende o apaga el modo a mano, SIN tocar el terminal.
|
|
56
|
-
*
|
|
57
|
-
* Las pruebas lo necesitan: entrar de verdad escribiría la secuencia de la
|
|
58
|
-
* pantalla alternativa en la consola de quien corre las pruebas y le dejaría el
|
|
59
|
-
* informe en una pantalla que desaparece al acabar.
|
|
60
|
-
*/
|
|
61
79
|
export function forzarPantallaFija(valor) {
|
|
62
80
|
forzado = valor;
|
|
63
81
|
}
|
|
64
82
|
export function enPantallaFija() {
|
|
65
83
|
return forzado ?? dentro;
|
|
66
84
|
}
|
|
85
|
+
/**
|
|
86
|
+
* Enciende el modo de árbol único. Devuelve si de verdad se encendió.
|
|
87
|
+
*
|
|
88
|
+
* EL BOOLEANO NO SOBRA, Y SE VOLVIÓ IMPRESCINDIBLE AL PONERLO POR DEFECTO
|
|
89
|
+
*
|
|
90
|
+
* Sin terminal —una salida redirigida a un archivo, un `chocolatito "tarea"` en
|
|
91
|
+
* un script, CI— aquí no se entra. Pero quien llama montaba el árbol de todas
|
|
92
|
+
* formas, y Ink sin terminal escribe su marco como texto suelto: la salida del
|
|
93
|
+
* programa sale con la caja de escribir dentro.
|
|
94
|
+
*
|
|
95
|
+
* Mientras esto iba detrás de una variable no pasaba nunca, porque nadie la pone
|
|
96
|
+
* en un script. De serie, es el caso normal.
|
|
97
|
+
*/
|
|
67
98
|
export function entrarEnPantallaFija() {
|
|
68
|
-
if (dentro
|
|
69
|
-
return;
|
|
99
|
+
if (dentro)
|
|
100
|
+
return true;
|
|
101
|
+
if (!process.stdout.isTTY)
|
|
102
|
+
return false;
|
|
70
103
|
dentro = true;
|
|
71
|
-
|
|
72
|
-
//
|
|
73
|
-
redirigirDibujo((texto) =>
|
|
74
|
-
// Y el pie deja de pintar. Sigue guardando sus secciones -el spinner y la
|
|
75
|
-
// linea de razonamiento publican ahi sin enterarse de nada- pero quien las
|
|
76
|
-
// dibuja pasa a ser el arbol. Dos dueños del mismo trozo de pantalla es
|
|
77
|
-
// exactamente el problema que esto viene a quitar.
|
|
104
|
+
// Lo que el agente dibuja pasa a ser texto de la transcripción. De ahí lo
|
|
105
|
+
// recoge <Static> y lo escribe en el historial del terminal, una sola vez.
|
|
106
|
+
redirigirDibujo((texto) => anotar(texto));
|
|
78
107
|
habilitarPie(false);
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
108
|
+
interceptarConsola();
|
|
109
|
+
return true;
|
|
110
|
+
}
|
|
111
|
+
const CANALES = ["log", "error", "warn", "info"];
|
|
112
|
+
/**
|
|
113
|
+
* `console.clear` va aparte porque no es un mensaje, es una orden al terminal.
|
|
114
|
+
*
|
|
115
|
+
* Y estaba fuera de la lista, que era un agujero de los caros: /clear, /cd y el
|
|
116
|
+
* Ctrl+L del prompt clásico llaman a `console.clear()`, y con el árbol montado
|
|
117
|
+
* eso borra filas que Ink cree suyas. A partir de ahí Ink repinta sobre un sitio
|
|
118
|
+
* que ya no existe y lo que se ve es basura.
|
|
119
|
+
*
|
|
120
|
+
* Se manda a `limpiarLaPantalla`, que hace lo mismo pero en el orden que no
|
|
121
|
+
* rompe nada. Ver ui/ink/montarApp.tsx.
|
|
122
|
+
*/
|
|
123
|
+
let clearOriginal = null;
|
|
124
|
+
/**
|
|
125
|
+
* Manda `console` a la transcripción.
|
|
126
|
+
*
|
|
127
|
+
* Se exporta para poder probarlo: `entrarEnPantallaFija` no se puede llamar en
|
|
128
|
+
* las pruebas porque exige un terminal de verdad, y un parche de consola sin
|
|
129
|
+
* probar es de las cosas que fallan en silencio —lo que se pierde no se ve, que
|
|
130
|
+
* es justo el problema—.
|
|
131
|
+
*/
|
|
132
|
+
export function interceptarConsola() {
|
|
133
|
+
if (original.log)
|
|
134
|
+
return;
|
|
135
|
+
clearOriginal = console.clear;
|
|
136
|
+
console.clear = () => {
|
|
137
|
+
limpiarLaPantalla();
|
|
82
138
|
};
|
|
139
|
+
for (const nombre of CANALES) {
|
|
140
|
+
original[nombre] = console[nombre];
|
|
141
|
+
console[nombre] = (...args) => {
|
|
142
|
+
anotar(`${format(...args)}\n`);
|
|
143
|
+
};
|
|
144
|
+
}
|
|
145
|
+
}
|
|
146
|
+
export function devolverConsola() {
|
|
147
|
+
if (clearOriginal) {
|
|
148
|
+
console.clear = clearOriginal;
|
|
149
|
+
clearOriginal = null;
|
|
150
|
+
}
|
|
151
|
+
for (const nombre of CANALES) {
|
|
152
|
+
const previo = original[nombre];
|
|
153
|
+
if (previo)
|
|
154
|
+
console[nombre] = previo;
|
|
155
|
+
delete original[nombre];
|
|
156
|
+
}
|
|
83
157
|
}
|
|
84
158
|
/**
|
|
85
159
|
* Devuelve el terminal como estaba.
|
|
86
160
|
*
|
|
87
|
-
*
|
|
88
|
-
*
|
|
89
|
-
*
|
|
161
|
+
* Aquí ya no hay ninguna pantalla que abandonar —esa era la versión de antes—,
|
|
162
|
+
* pero sí hay que devolver el conducto de dibujo y el pie: si el proceso sigue
|
|
163
|
+
* vivo después de esto (una prueba, una sesión que cambia de modo) y el dibujo
|
|
164
|
+
* se queda desviado, todo lo que se escriba va a una transcripción que ya no
|
|
165
|
+
* pinta nadie.
|
|
90
166
|
*/
|
|
91
167
|
export function salirDePantallaFija() {
|
|
92
168
|
if (!dentro)
|
|
93
169
|
return;
|
|
94
170
|
dentro = false;
|
|
95
|
-
if (logOriginal) {
|
|
96
|
-
console.log = logOriginal;
|
|
97
|
-
logOriginal = null;
|
|
98
|
-
}
|
|
99
171
|
redirigirDibujo(null);
|
|
100
172
|
habilitarPie(null);
|
|
101
|
-
|
|
102
|
-
process.stdout.write(SALIR);
|
|
103
|
-
}
|
|
104
|
-
catch { }
|
|
173
|
+
devolverConsola();
|
|
105
174
|
}
|
|
106
175
|
process.on("exit", salirDePantallaFija);
|
|
107
|
-
|
|
108
|
-
* UN
|
|
176
|
+
/*
|
|
177
|
+
* AQUÍ HABÍA UN `unhandledRejection` QUE MATABA EL PROGRAMA. SE HA QUITADO.
|
|
178
|
+
*
|
|
179
|
+
* Existía para que un error dentro de la pantalla alternativa no se perdiera al
|
|
180
|
+
* salir de ella. Pero se registraba al importar el módulo, o sea SIEMPRE, con
|
|
181
|
+
* pantalla fija o sin ella, y hacía `process.exit(1)`.
|
|
109
182
|
*
|
|
110
|
-
*
|
|
111
|
-
*
|
|
112
|
-
* la
|
|
113
|
-
*
|
|
183
|
+
* index.ts tiene su propia red de seguridad para lo mismo, y su criterio es el
|
|
184
|
+
* contrario y el bueno: "una promesa sin capturar no debería costarle al usuario
|
|
185
|
+
* la sesión entera, con todo su contexto. Se avisa y se sigue." Node ejecuta los
|
|
186
|
+
* dos manejadores, pero el de aquí se registraba antes y salía, así que ganaba
|
|
187
|
+
* siempre.
|
|
114
188
|
*
|
|
115
|
-
*
|
|
116
|
-
*
|
|
189
|
+
* Consecuencia en la versión publicada: cualquier promesa de fondo que fallara
|
|
190
|
+
* —un servidor MCP que no levanta, el chequeo de licencia, la comprobación de
|
|
191
|
+
* actualizaciones— cerraba Chocolatito de golpe. Sin mensaje, y sin tener nada
|
|
192
|
+
* que ver con la interfaz.
|
|
117
193
|
*
|
|
118
|
-
*
|
|
119
|
-
*
|
|
120
|
-
*
|
|
194
|
+
* Con el buffer normal el motivo original ya no existe: un error impreso se
|
|
195
|
+
* queda en pantalla, porque no hay ninguna pantalla que se lleve el mensaje al
|
|
196
|
+
* cerrarse.
|
|
121
197
|
*/
|
|
122
|
-
function contarLoQueFallo(err) {
|
|
123
|
-
salirDePantallaFija();
|
|
124
|
-
const detalle = err instanceof Error ? `${err.message}\n${err.stack ?? ""}` : String(err);
|
|
125
|
-
try {
|
|
126
|
-
fs.writeFileSync(path.join(os.homedir(), ".chocolatito-error.txt"), `${new Date().toISOString()}\n${detalle}\n`, "utf-8");
|
|
127
|
-
}
|
|
128
|
-
catch { }
|
|
129
|
-
process.stderr.write(`\nChocolatito se cerro por un error:\n${detalle}\n`);
|
|
130
|
-
process.stderr.write(`Guardado en ${path.join(os.homedir(), ".chocolatito-error.txt")}\n`);
|
|
131
|
-
}
|
|
132
|
-
process.on("uncaughtException", (err) => {
|
|
133
|
-
contarLoQueFallo(err);
|
|
134
|
-
process.exit(1);
|
|
135
|
-
});
|
|
136
|
-
process.on("unhandledRejection", (err) => {
|
|
137
|
-
contarLoQueFallo(err);
|
|
138
|
-
process.exit(1);
|
|
139
|
-
});
|
|
@@ -4,23 +4,6 @@ export interface PermissionPromptResult {
|
|
|
4
4
|
userFeedback?: string;
|
|
5
5
|
}
|
|
6
6
|
export declare function setAutoApprove(value: boolean): void;
|
|
7
|
-
/**
|
|
8
|
-
* DIALOGO DE PERMISO
|
|
9
|
-
*
|
|
10
|
-
* La version anterior tenia dos fallos visibles en cuanto se usaba:
|
|
11
|
-
*
|
|
12
|
-
* 1. Al mover la seleccion subia el cursor 12 lineas fijas, pero la caja mide
|
|
13
|
-
* entre 10 y 14 segun cuantos detalles tenga. Cada flecha dejaba media caja
|
|
14
|
-
* huerfana en pantalla, y por eso salian marcos vacios apilados.
|
|
15
|
-
*
|
|
16
|
-
* 2. El titulo llevaba un simbolo de anchura ambigua. El terminal lo pinta
|
|
17
|
-
* ocupando dos columnas y el calculo del ancho contaba una, asi que el borde
|
|
18
|
-
* derecho quedaba descuadrado justo en esa linea.
|
|
19
|
-
*
|
|
20
|
-
* Aqui se dibuja la caja a mano, con anchura conocida, y se repinta subiendo
|
|
21
|
-
* exactamente las lineas que se escribieron.
|
|
22
|
-
*/
|
|
23
|
-
export declare function askToolPermission(toolName: string, args: Record<string, any>, cwd?: string): Promise<PermissionPromptResult>;
|
|
24
7
|
export declare const PERMISSION_OPTIONS: {
|
|
25
8
|
label: string;
|
|
26
9
|
hint: string;
|
|
@@ -33,3 +16,13 @@ export declare const PERMISSION_OPTIONS: {
|
|
|
33
16
|
* derecho no se ve leyendo el codigo, solo ejecutandolo.
|
|
34
17
|
*/
|
|
35
18
|
export declare function buildPermissionBox(toolName: string, args: Record<string, any>, cwd: string, selectedIndex: number, width?: number): string[];
|
|
19
|
+
/**
|
|
20
|
+
* Se pide el terminal prestado antes de abrir esto.
|
|
21
|
+
*
|
|
22
|
+
* Con el árbol de Ink montado hay un dueño de la pantalla, y esta función es de
|
|
23
|
+
* las que necesitan el teclado para ellas solas: escribe directo a stdout y abre
|
|
24
|
+
* su propia lectura de teclas. Sin el préstamo, las dos cuentas de filas se pisan
|
|
25
|
+
* y el marco de Ink no se recupera. Sin árbol, `conElTerminalPrestado` ejecuta la
|
|
26
|
+
* tarea tal cual y no cuesta nada. Ver ui/ink/prestamo.ts.
|
|
27
|
+
*/
|
|
28
|
+
export declare function askToolPermission(toolName: string, args: Record<string, any>, cwd?: string): Promise<PermissionPromptResult>;
|
|
@@ -3,6 +3,7 @@ import process from "node:process";
|
|
|
3
3
|
import chalk from "chalk";
|
|
4
4
|
import { cycleMode, describeMode, getMode, modeAnnouncement } from "./modes.js";
|
|
5
5
|
import { isOutsideProject, isSvgSource } from "../config/permissions.js";
|
|
6
|
+
import { conElTerminalPrestado } from "./ink/prestamo.js";
|
|
6
7
|
/**
|
|
7
8
|
* Aprobacion automatica: se activa con --yes / -y o con la variable de entorno
|
|
8
9
|
* CHOCOLATITO_AUTO_APPROVE. Pensada para modo no interactivo y CI.
|
|
@@ -27,7 +28,7 @@ export function setAutoApprove(value) {
|
|
|
27
28
|
* Aqui se dibuja la caja a mano, con anchura conocida, y se repinta subiendo
|
|
28
29
|
* exactamente las lineas que se escribieron.
|
|
29
30
|
*/
|
|
30
|
-
|
|
31
|
+
async function askToolPermissionDirecto(toolName, args, cwd = process.cwd()) {
|
|
31
32
|
if (autoApprove) {
|
|
32
33
|
return { approved: true };
|
|
33
34
|
}
|
|
@@ -351,3 +352,15 @@ function details(toolName, args, cwd, width) {
|
|
|
351
352
|
out.push({ text: "", length: 0 });
|
|
352
353
|
return out;
|
|
353
354
|
}
|
|
355
|
+
/**
|
|
356
|
+
* Se pide el terminal prestado antes de abrir esto.
|
|
357
|
+
*
|
|
358
|
+
* Con el árbol de Ink montado hay un dueño de la pantalla, y esta función es de
|
|
359
|
+
* las que necesitan el teclado para ellas solas: escribe directo a stdout y abre
|
|
360
|
+
* su propia lectura de teclas. Sin el préstamo, las dos cuentas de filas se pisan
|
|
361
|
+
* y el marco de Ink no se recupera. Sin árbol, `conElTerminalPrestado` ejecuta la
|
|
362
|
+
* tarea tal cual y no cuesta nada. Ver ui/ink/prestamo.ts.
|
|
363
|
+
*/
|
|
364
|
+
export function askToolPermission(toolName, args, cwd = process.cwd()) {
|
|
365
|
+
return conElTerminalPrestado(() => askToolPermissionDirecto(toolName, args, cwd));
|
|
366
|
+
}
|
package/dist/ui/pieFijo.js
CHANGED
|
@@ -219,10 +219,24 @@ function anotar(nombre, lineas) {
|
|
|
219
219
|
* veces por segundo y la barra de escribir casi nunca cambia entre dos.
|
|
220
220
|
*/
|
|
221
221
|
export function fijarSeccion(nombre, lineas) {
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
if (
|
|
225
|
-
|
|
222
|
+
// DELEGA, Y ESO ARREGLA UN FALLO GORDO
|
|
223
|
+
//
|
|
224
|
+
// Antes empezaba con `if (!pieUsable()) return;`, o sea que con el pie apagado
|
|
225
|
+
// -que es exactamente lo que pasa cuando manda el arbol de Ink- esta funcion no
|
|
226
|
+
// hacia NADA. Ni guardaba la seccion ni avisaba a quien la pinta.
|
|
227
|
+
//
|
|
228
|
+
// Dos consecuencias, las dos visibles:
|
|
229
|
+
//
|
|
230
|
+
// - La linea de razonamiento (el 💭) es el unico sitio que llama aqui
|
|
231
|
+
// (ui/reasoningStream.ts:122). Con el arbol montado no salia nunca.
|
|
232
|
+
// - `quitarSeccion` pasa por aqui. Asi que `quitarSeccion("spinner")` al
|
|
233
|
+
// acabar el turno tampoco hacia nada: el "✳ Trabajando…" se quedaba
|
|
234
|
+
// puesto para siempre, mucho despues de que el agente hubiera terminado.
|
|
235
|
+
// Eso es lo que se ve como "se queda trabado".
|
|
236
|
+
//
|
|
237
|
+
// `fijarSecciones` ya distingue bien las dos cosas -guardar y avisar SIEMPRE,
|
|
238
|
+
// pintar solo si el pie esta encendido-, asi que aqui basta con delegar.
|
|
239
|
+
fijarSecciones([[nombre, lineas]]);
|
|
226
240
|
}
|
|
227
241
|
/**
|
|
228
242
|
* Varias secciones de una vez, con UN solo repintado.
|
|
@@ -312,6 +326,14 @@ export function soltarPie() {
|
|
|
312
326
|
return;
|
|
313
327
|
secciones.clear();
|
|
314
328
|
repintar("");
|
|
329
|
+
// Y se avisa, que si no el arbol sigue pintando una barra que ya no existe
|
|
330
|
+
// hasta que otra cosa cualquiera le haga redibujar.
|
|
331
|
+
for (const cb of alCambiarElPie) {
|
|
332
|
+
try {
|
|
333
|
+
cb();
|
|
334
|
+
}
|
|
335
|
+
catch { }
|
|
336
|
+
}
|
|
315
337
|
}
|
|
316
338
|
/**
|
|
317
339
|
* Olvida el estado sin tocar la pantalla.
|
package/dist/ui/selector.d.ts
CHANGED
|
@@ -28,10 +28,12 @@ export interface OpcionDeLista {
|
|
|
28
28
|
detalle?: string;
|
|
29
29
|
}
|
|
30
30
|
/**
|
|
31
|
-
*
|
|
31
|
+
* Se pide el terminal prestado antes de abrir esto.
|
|
32
32
|
*
|
|
33
|
-
*
|
|
34
|
-
*
|
|
35
|
-
*
|
|
33
|
+
* Con el árbol de Ink montado hay un dueño de la pantalla, y esta función es de
|
|
34
|
+
* las que necesitan el teclado para ellas solas: escribe directo a stdout y abre
|
|
35
|
+
* su propia lectura de teclas. Sin el préstamo, las dos cuentas de filas se pisan
|
|
36
|
+
* y el marco de Ink no se recupera. Sin árbol, `conElTerminalPrestado` ejecuta la
|
|
37
|
+
* tarea tal cual y no cuesta nada. Ver ui/ink/prestamo.ts.
|
|
36
38
|
*/
|
|
37
39
|
export declare function elegirDeLista(titulo: string, opciones: OpcionDeLista[], indiceInicial?: number): Promise<string | null>;
|
package/dist/ui/selector.js
CHANGED
|
@@ -2,6 +2,7 @@ import chalk from "chalk";
|
|
|
2
2
|
import process from "node:process";
|
|
3
3
|
import readline from "node:readline";
|
|
4
4
|
import { dibujar } from "./salida.js";
|
|
5
|
+
import { conElTerminalPrestado } from "./ink/prestamo.js";
|
|
5
6
|
/**
|
|
6
7
|
* Enseña la lista y devuelve el id elegido. `null` si se sale con Esc.
|
|
7
8
|
*
|
|
@@ -9,7 +10,7 @@ import { dibujar } from "./salida.js";
|
|
|
9
10
|
* quedarse esperando una tecla que no va a llegar nunca. Es lo que pasaria al
|
|
10
11
|
* correrlo desde un script o dentro de las pruebas.
|
|
11
12
|
*/
|
|
12
|
-
|
|
13
|
+
async function elegirDeListaDirecto(titulo, opciones, indiceInicial = 0) {
|
|
13
14
|
if (opciones.length === 0)
|
|
14
15
|
return null;
|
|
15
16
|
if (!process.stdin.isTTY)
|
|
@@ -89,3 +90,15 @@ export async function elegirDeLista(titulo, opciones, indiceInicial = 0) {
|
|
|
89
90
|
process.stdin.on("keypress", alPulsar);
|
|
90
91
|
});
|
|
91
92
|
}
|
|
93
|
+
/**
|
|
94
|
+
* Se pide el terminal prestado antes de abrir esto.
|
|
95
|
+
*
|
|
96
|
+
* Con el árbol de Ink montado hay un dueño de la pantalla, y esta función es de
|
|
97
|
+
* las que necesitan el teclado para ellas solas: escribe directo a stdout y abre
|
|
98
|
+
* su propia lectura de teclas. Sin el préstamo, las dos cuentas de filas se pisan
|
|
99
|
+
* y el marco de Ink no se recupera. Sin árbol, `conElTerminalPrestado` ejecuta la
|
|
100
|
+
* tarea tal cual y no cuesta nada. Ver ui/ink/prestamo.ts.
|
|
101
|
+
*/
|
|
102
|
+
export function elegirDeLista(titulo, opciones, indiceInicial = 0) {
|
|
103
|
+
return conElTerminalPrestado(() => elegirDeListaDirecto(titulo, opciones, indiceInicial));
|
|
104
|
+
}
|
package/extension/manifest.json
CHANGED
|
@@ -1,60 +1,60 @@
|
|
|
1
|
-
{
|
|
2
|
-
"manifest_version": 3,
|
|
3
|
-
"minimum_chrome_version": "102",
|
|
4
|
-
"name": "Chocolatito Code",
|
|
5
|
-
"version": "1.6.
|
|
6
|
-
"description": "Deja que Chocolatito Code trabaje dentro de tu Chrome, en segundo plano y con tus sesiones ya iniciadas.",
|
|
7
|
-
"permissions": [
|
|
8
|
-
"tabs",
|
|
9
|
-
"tabGroups",
|
|
10
|
-
"scripting",
|
|
11
|
-
"debugger",
|
|
12
|
-
"webNavigation",
|
|
13
|
-
"storage",
|
|
14
|
-
"downloads"
|
|
15
|
-
],
|
|
16
|
-
"host_permissions": [
|
|
17
|
-
"<all_urls>"
|
|
18
|
-
],
|
|
19
|
-
"icons": {
|
|
20
|
-
"16": "iconos/16.png",
|
|
21
|
-
"32": "iconos/32.png",
|
|
22
|
-
"48": "iconos/48.png",
|
|
23
|
-
"128": "iconos/128.png"
|
|
24
|
-
},
|
|
25
|
-
"background": {
|
|
26
|
-
"service_worker": "background.js"
|
|
27
|
-
},
|
|
28
|
-
"content_scripts": [
|
|
29
|
-
{
|
|
30
|
-
"matches": [
|
|
31
|
-
"<all_urls>"
|
|
32
|
-
],
|
|
33
|
-
"js": [
|
|
34
|
-
"content.js"
|
|
35
|
-
],
|
|
36
|
-
"run_at": "document_idle",
|
|
37
|
-
"all_frames": true
|
|
38
|
-
}
|
|
39
|
-
],
|
|
40
|
-
"action": {
|
|
41
|
-
"default_title": "Chocolatito Code",
|
|
42
|
-
"default_popup": "popup.html",
|
|
43
|
-
"default_icon": {
|
|
44
|
-
"16": "iconos/16.png",
|
|
45
|
-
"32": "iconos/32.png",
|
|
46
|
-
"48": "iconos/48.png"
|
|
47
|
-
}
|
|
48
|
-
},
|
|
49
|
-
"web_accessible_resources": [
|
|
50
|
-
{
|
|
51
|
-
"resources": [
|
|
52
|
-
"iconos/*",
|
|
53
|
-
"fuentes/*"
|
|
54
|
-
],
|
|
55
|
-
"matches": [
|
|
56
|
-
"<all_urls>"
|
|
57
|
-
]
|
|
58
|
-
}
|
|
59
|
-
]
|
|
60
|
-
}
|
|
1
|
+
{
|
|
2
|
+
"manifest_version": 3,
|
|
3
|
+
"minimum_chrome_version": "102",
|
|
4
|
+
"name": "Chocolatito Code",
|
|
5
|
+
"version": "1.6.7",
|
|
6
|
+
"description": "Deja que Chocolatito Code trabaje dentro de tu Chrome, en segundo plano y con tus sesiones ya iniciadas.",
|
|
7
|
+
"permissions": [
|
|
8
|
+
"tabs",
|
|
9
|
+
"tabGroups",
|
|
10
|
+
"scripting",
|
|
11
|
+
"debugger",
|
|
12
|
+
"webNavigation",
|
|
13
|
+
"storage",
|
|
14
|
+
"downloads"
|
|
15
|
+
],
|
|
16
|
+
"host_permissions": [
|
|
17
|
+
"<all_urls>"
|
|
18
|
+
],
|
|
19
|
+
"icons": {
|
|
20
|
+
"16": "iconos/16.png",
|
|
21
|
+
"32": "iconos/32.png",
|
|
22
|
+
"48": "iconos/48.png",
|
|
23
|
+
"128": "iconos/128.png"
|
|
24
|
+
},
|
|
25
|
+
"background": {
|
|
26
|
+
"service_worker": "background.js"
|
|
27
|
+
},
|
|
28
|
+
"content_scripts": [
|
|
29
|
+
{
|
|
30
|
+
"matches": [
|
|
31
|
+
"<all_urls>"
|
|
32
|
+
],
|
|
33
|
+
"js": [
|
|
34
|
+
"content.js"
|
|
35
|
+
],
|
|
36
|
+
"run_at": "document_idle",
|
|
37
|
+
"all_frames": true
|
|
38
|
+
}
|
|
39
|
+
],
|
|
40
|
+
"action": {
|
|
41
|
+
"default_title": "Chocolatito Code",
|
|
42
|
+
"default_popup": "popup.html",
|
|
43
|
+
"default_icon": {
|
|
44
|
+
"16": "iconos/16.png",
|
|
45
|
+
"32": "iconos/32.png",
|
|
46
|
+
"48": "iconos/48.png"
|
|
47
|
+
}
|
|
48
|
+
},
|
|
49
|
+
"web_accessible_resources": [
|
|
50
|
+
{
|
|
51
|
+
"resources": [
|
|
52
|
+
"iconos/*",
|
|
53
|
+
"fuentes/*"
|
|
54
|
+
],
|
|
55
|
+
"matches": [
|
|
56
|
+
"<all_urls>"
|
|
57
|
+
]
|
|
58
|
+
}
|
|
59
|
+
]
|
|
60
|
+
}
|
package/package.json
CHANGED
package/dist/ui/historial.d.ts
DELETED
|
@@ -1,49 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* LO QUE HA SALIDO POR PANTALLA, GUARDADO EN MEMORIA
|
|
3
|
-
*
|
|
4
|
-
* POR QUE HACE FALTA
|
|
5
|
-
*
|
|
6
|
-
* En la pantalla normal el historial lo lleva el terminal: sale una línea, se va
|
|
7
|
-
* hacia arriba, y la rueda del ratón la recupera. Por eso la barra de abajo sube
|
|
8
|
-
* con el scroll: es una línea más del historial, no una capa encima.
|
|
9
|
-
*
|
|
10
|
-
* En la pantalla alternativa —la que usan vim o htop— el terminal NO guarda
|
|
11
|
-
* nada. A cambio, la barra se queda clavada de verdad. Pero si nadie recuerda lo
|
|
12
|
-
* que salió, la conversación desaparece en cuanto pasa de una pantalla, que sería
|
|
13
|
-
* mucho peor que el problema que se quiere resolver.
|
|
14
|
-
*
|
|
15
|
-
* Así que aquí se guarda. Es el precio de tener la barra fija: el historial deja
|
|
16
|
-
* de ser del terminal y pasa a ser nuestro.
|
|
17
|
-
*
|
|
18
|
-
* POR QUE SE GUARDA POR LÍNEAS Y NO EL FLUJO CRUDO
|
|
19
|
-
*
|
|
20
|
-
* Lo que llega trae códigos de color y a veces medio renglón sin terminar. Para
|
|
21
|
-
* poder pintar "las últimas N líneas" hay que saber dónde acaba cada una, así
|
|
22
|
-
* que se parte por saltos y el resto sin terminar se queda esperando al suyo.
|
|
23
|
-
* Los colores se conservan tal cual: recortarlos aquí sería pintar la
|
|
24
|
-
* conversación en gris.
|
|
25
|
-
*/
|
|
26
|
-
/** Añade lo que se acaba de escribir. Acepta trozos a medio renglón. */
|
|
27
|
-
export declare function apuntar(texto: string): void;
|
|
28
|
-
/**
|
|
29
|
-
* Todas las líneas, con el resto sin terminar como última.
|
|
30
|
-
*
|
|
31
|
-
* Se incluye a propósito: mientras el modelo escribe una frase larga, el resto
|
|
32
|
-
* ES lo que está saliendo. Ocultarlo hasta el salto haría que la respuesta
|
|
33
|
-
* apareciera a tirones, un renglón entero de golpe.
|
|
34
|
-
*/
|
|
35
|
-
export declare function todas(): string[];
|
|
36
|
-
export declare function cuantas(): number;
|
|
37
|
-
/** Se llama en cada escritura, para que quien pinte se entere. */
|
|
38
|
-
export declare function alEscribir(cb: () => void): () => void;
|
|
39
|
-
export declare function vaciar(): void;
|
|
40
|
-
/**
|
|
41
|
-
* La ventana visible: `alto` líneas terminando `desdeElFinal` por encima del
|
|
42
|
-
* final.
|
|
43
|
-
*
|
|
44
|
-
* `desdeElFinal` es cuánto se ha subido con el scroll. Cero es el fondo, que es
|
|
45
|
-
* donde se está mientras se trabaja.
|
|
46
|
-
*/
|
|
47
|
-
export declare function ventana(alto: number, desdeElFinal?: number): string[];
|
|
48
|
-
/** Cuánto se puede subir todavía. Sirve para no pasarse del principio. */
|
|
49
|
-
export declare function tope(alto: number): number;
|