@openvertice/bot-sdk 0.0.0-stage → 0.1.0

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.
Files changed (48) hide show
  1. package/README.md +189 -2
  2. package/dist/src/audio.d.ts +32 -0
  3. package/dist/src/audio.d.ts.map +1 -0
  4. package/dist/src/audio.js +47 -0
  5. package/dist/src/audio.js.map +1 -0
  6. package/dist/src/cliente.d.ts +213 -0
  7. package/dist/src/cliente.d.ts.map +1 -0
  8. package/dist/src/cliente.js +381 -0
  9. package/dist/src/cliente.js.map +1 -0
  10. package/dist/src/gateway.d.ts +76 -0
  11. package/dist/src/gateway.d.ts.map +1 -0
  12. package/dist/src/gateway.js +299 -0
  13. package/dist/src/gateway.js.map +1 -0
  14. package/dist/src/http.d.ts +119 -0
  15. package/dist/src/http.d.ts.map +1 -0
  16. package/dist/src/http.js +189 -0
  17. package/dist/src/http.js.map +1 -0
  18. package/dist/src/index.d.ts +19 -0
  19. package/dist/src/index.d.ts.map +1 -0
  20. package/dist/src/index.js +16 -0
  21. package/dist/src/index.js.map +1 -0
  22. package/dist/src/tipos.d.ts +243 -0
  23. package/dist/src/tipos.d.ts.map +1 -0
  24. package/dist/src/tipos.js +5 -0
  25. package/dist/src/tipos.js.map +1 -0
  26. package/dist/src/voz-wrtc.d.ts +20 -0
  27. package/dist/src/voz-wrtc.d.ts.map +1 -0
  28. package/dist/src/voz-wrtc.js +68 -0
  29. package/dist/src/voz-wrtc.js.map +1 -0
  30. package/dist/src/voz.d.ts +150 -0
  31. package/dist/src/voz.d.ts.map +1 -0
  32. package/dist/src/voz.js +311 -0
  33. package/dist/src/voz.js.map +1 -0
  34. package/dist/src/wav.d.ts +29 -0
  35. package/dist/src/wav.d.ts.map +1 -0
  36. package/dist/src/wav.js +54 -0
  37. package/dist/src/wav.js.map +1 -0
  38. package/package.json +58 -3
  39. package/src/audio.ts +88 -0
  40. package/src/cliente.ts +472 -0
  41. package/src/gateway.ts +354 -0
  42. package/src/http.ts +249 -0
  43. package/src/index.ts +41 -0
  44. package/src/tipos.ts +220 -0
  45. package/src/voz-wrtc.ts +100 -0
  46. package/src/voz.ts +407 -0
  47. package/src/wav.ts +71 -0
  48. package/src/wrtc.d.ts +4 -0
package/README.md CHANGED
@@ -1,3 +1,190 @@
1
- # Temporary Holding Version
1
+ # `@openvertice/bot-sdk`
2
2
 
3
- This version is a temporary placeholder for this package. An operational version to replace this has been submitted for review and is awaiting a staged release.
3
+ Escreva um bot para o Vértice: ele entra num canal de texto, responde a
4
+ comandos e — quando você quiser — entra na sala de voz como mais um par da
5
+ malha, publicando áudio de verdade.
6
+
7
+ O contrato do servidor (versão `2026-10`) vive em `server/bots/README.md`, no
8
+ repositório do Vértice. Este pacote é um cliente desse contrato, não uma segunda
9
+ verdade: se os dois discordarem, o servidor está certo.
10
+
11
+ ## Instalar
12
+
13
+ ```bash
14
+ npm i @openvertice/bot-sdk # texto
15
+ npm i @openvertice/bot-sdk @roamhq/wrtc # texto + voz
16
+ ```
17
+
18
+ Node **22 ou mais novo**. Para texto, o SDK não tem dependência nenhuma: usa o
19
+ `WebSocket` e o `fetch` do próprio Node. `@roamhq/wrtc` é opcional e só é
20
+ carregado quando alguém usa voz (no Node 24 ele vem com binário pronto —
21
+ verificado: ABI 137, sem compilar nada).
22
+
23
+ ## Criar o bot
24
+
25
+ 1. Abra o painel administrativo (`VERTICE_ADMIN_PORT` + `VERTICE_ADMIN_SENHA`).
26
+ 2. Aba **Bots** → dê um nome, marque os canais de texto (com `escutar`/`falar`)
27
+ e os de voz.
28
+ 3. Copie o token `vtb_…` **na hora**: ele aparece uma única vez.
29
+ 4. Guarde no `.env` da raiz do pacote (`cp .env.example .env`) — os exemplos
30
+ leem de lá. Rodar `npm run eco` com o token só no arquivo funciona.
31
+
32
+ Se você não quer manter um processo rodando, o painel também gera um **webhook**
33
+ (`POST /api/bots/webhook/<segredo>?canal=CODE`, corpo = texto): serve para
34
+ publicar em nome do bot a partir de outro sistema. É credencial separada do
35
+ token.
36
+
37
+ ## Texto
38
+
39
+ ```ts
40
+ import { Bot } from "@openvertice/bot-sdk";
41
+
42
+ const bot = new Bot({
43
+ token: process.env.VERTICE_BOT_TOKEN!,
44
+ baseUrl: "http://localhost:8080",
45
+ intents: ["MESSAGES"],
46
+ });
47
+
48
+ bot.on("message.created", (m) => {
49
+ if (m.autorBot) return; // sem isso o bot conversa consigo mesmo
50
+ console.log(`${m.autor}: ${m.texto}`);
51
+ });
52
+
53
+ bot.command("ping", { descricao: "responde pong" }, async ({ responder }) => {
54
+ await responder("pong");
55
+ });
56
+
57
+ await bot.start();
58
+ ```
59
+
60
+ - `bot.on(evento, fn)` — `ready`, `message.created`, `message.deleted`,
61
+ `mention`, `voice.joined`, `voice.left`, `voice.signal`,
62
+ `voice.peer.joined`, `voice.peer.left`, `error`.
63
+ - `bot.command(nome, fn)` / `bot.command(nome, { descricao, canais }, fn)` — o
64
+ prefixo (`!`) é do canal, não do comando. O bot **não** executa os próprios
65
+ comandos.
66
+ - Os comandos registrados são anunciados no `identify`: o cliente completa
67
+ `!to` → `!tocar` no compositor, com a descrição ao lado. Registrar depois de
68
+ `start()` também aparece — sem reconectar (`bot.comandos` é a lista viva).
69
+ - `await bot.enviar("MURAL", "oi")` — devolve o item criado (id, horário).
70
+ - `await bot.enviarVoz("MURAL", wav)` — manda áudio como **mensagem de voz**;
71
+ `enviarArquivo(canal, bytes, { nome, mime })` faz o mesmo como anexo comum.
72
+ - `await bot.historico("MURAL", antesDe?)` e `bot.apagar("MURAL", id)`.
73
+ - `bot.agir(tipo, dados)` — ação crua no gateway (a voz usa por baixo).
74
+
75
+ O SDK cuida do que ninguém quer escrever duas vezes: troca o token por sessão,
76
+ renova antes de vencer, manda batimento, retoma com `resume` e reconecta com
77
+ espera crescente. Token girado, bot desativado ou outra conexão assumindo o
78
+ mesmo bot **não** reconectam: `bot.estado` vira `recusado` e o erro fica em
79
+ `bot.ultimoErro`.
80
+
81
+ ## Mensagem de voz (áudio no chat)
82
+
83
+ ```ts
84
+ import { Bot, wavDeTom } from "@openvertice/bot-sdk";
85
+
86
+ const wav = wavDeTom({ segundos: 1, frequencia: 440 }); // Uint8Array PCM 16 bits
87
+ const mensagem = await bot.enviarVoz("MURAL", wav, { nome: "recado.wav" });
88
+ mensagem.tipo; // "voz"
89
+ mensagem.arquivo?.url; // /chat/arquivos/<id>?exp=…&sig=… (pronta para <audio>)
90
+ ```
91
+
92
+ O corpo vai cru, com o tipo no cabeçalho — não há multipart. Para um arquivo
93
+ que não seja voz, use `enviarArquivo` (sem `X-Vertice-Tipo`). O limite é o do
94
+ chat (`VERTICE_CHAT_MAX_MB`) e a rajada de 30 mensagens por minuto vale igual.
95
+
96
+ ## Ser chamado com `@`
97
+
98
+ ```ts
99
+ bot.on("mention", async (m) => {
100
+ if (m.autorBot) return;
101
+ await bot.enviar(m.sala!, `oi, ${m.autor}!`);
102
+ });
103
+ ```
104
+
105
+ `mention` chega quando alguém escreve `@login` ou `@nome de exibição` (sem
106
+ caixa nem acento) e o bot tem o canal com `escutar`. Ele **atravessa o prefixo**
107
+ do canal — é o que deixa chamar o bot numa sala de comandos (`!`) sem que ele
108
+ leia a conversa toda. Em canal sem prefixo, `mention` vem junto com
109
+ `message.created` (mesmo `id`): trate como aviso, não como segunda mensagem.
110
+
111
+ ## Voz
112
+
113
+ ```ts
114
+ import { Bot, Voz, criarTransporteWrtc, tocarTom } from "@openvertice/bot-sdk";
115
+
116
+ const bot = new Bot({ token, intents: ["MESSAGES"] });
117
+ await bot.start();
118
+
119
+ const transporte = await criarTransporteWrtc();
120
+ // A track sai da fonte que você alimenta; sem `track` a `Voz` cria outra fonte
121
+ // e o bot publica silêncio.
122
+ const fonte = transporte.criarFonteDeAudio();
123
+ const voz = new Voz(bot, { transporte, track: fonte.createTrack() });
124
+ const parar = tocarTom({ fonte, frequencia: 440 });
125
+
126
+ await voz.entrar("PATIO"); // resolve no `voice.joined`
127
+ voz.sair();
128
+ parar();
129
+ ```
130
+
131
+ O bot entra **só quando pede** — `start()` nunca entra na voz. O layout dos
132
+ transceivers é o mesmo dos clientes (`audio[0]` = microfone, `audio[1]` = som da
133
+ transmissão, `video[0]` = tela) e a oferta cruzada é resolvida pelo id, como nos
134
+ dois lados. `aoReceberTrack` recebe o áudio dos outros pares, se você quiser
135
+ monitorar ou gravar.
136
+
137
+ `@roamhq/wrtc` exige blocos de **480 amostras** em 48 kHz (10 ms) no
138
+ `RTCAudioSource` — é o que `tocarTom` faz; lendo arquivo, respeite o mesmo
139
+ tamanho.
140
+
141
+ ## Exemplos
142
+
143
+ ```bash
144
+ npm run build
145
+ cp .env.example .env # e edite o VERTICE_BOT_TOKEN
146
+ npm run eco # repete e responde !ping
147
+ npm run radio # !entrar toca um tom na voz
148
+ npm run recado # !recado manda áudio no chat
149
+ ```
150
+
151
+ Os exemplos carregam o `.env` da raiz do pacote na partida (com o leitor nativo
152
+ do Node — nada de `dotenv`). Variável do ambiente ganha do arquivo, então
153
+ `VERTICE_BOT_TOKEN=vtb_… npm run eco` também funciona — e é o que vale se você
154
+ rodar `node dist/exemplos/eco.js` de outro diretório.
155
+
156
+ ## Testes
157
+
158
+ Os testes de fumaça sobem o servidor de verdade (precisa do repositório do
159
+ Vértice ao lado):
160
+
161
+ ```bash
162
+ node testes/fumaca.mjs # dois bots: comando, histórico, apagar, eventos
163
+ node testes/voz.mjs # dois bots na voz: ICE + DTLS fechados, track recebida
164
+ node testes/voz-cliente.mjs # bot ↔ cliente do navegador: SDP nos dois nomes e áudio
165
+ # (o fumaca.mjs também manda um recado de voz e baixa o áudio de volta)
166
+ ```
167
+
168
+ ## Limites (do servidor, não do SDK)
169
+
170
+ - 30 mensagens por minuto por bot; 1 sessão por minuto (o SDK só pede outra
171
+ quando a atual está para vencer).
172
+ - O bot só vê os canais marcados no painel e, com prefixo, só o que começa por
173
+ ele.
174
+ - Bot não é conta: não aparece na gestão de membros, não recebe cargo e não
175
+ apaga mensagem de outra pessoa.
176
+
177
+ ## Publicar no npm
178
+
179
+ O pacote vai para o escopo `@openvertice` como **público** (`publishConfig.access`):
180
+
181
+ ```bash
182
+ npm login # conta com acesso à org @openvertice
183
+ npm run build # o `prepack` também compila durante o publish
184
+ npm pack --dry-run # confere exatamente o que entra no tarball
185
+ npm publish # @openvertice/bot-sdk@<versão>
186
+ ```
187
+
188
+ O tarball leva `dist/src` (JS + `.d.ts`), `src` (para os source maps) e este
189
+ README. Testes, exemplos, `.env` e `node_modules` ficam de fora. Para publicar
190
+ uma versão nova: `npm version patch|minor|major` e `npm publish`.
@@ -0,0 +1,32 @@
1
+ import type { FonteDeAudio } from "./voz.js";
2
+ /** Everything `tocarTom` needs in order to publish a sine wave. */
3
+ export interface OpcoesDoTom {
4
+ /** The transport source (`transporte.criarFonteDeAudio()`). */
5
+ fonte: FonteDeAudio;
6
+ /** Frequency in Hz. 440 is concert A. */
7
+ frequencia?: number;
8
+ /** 0…1. Anything above 0.5 starts to clip and distort. */
9
+ amplitude?: number;
10
+ /** 48 kHz: wrtc requires blocks of 480 samples. */
11
+ sampleRate?: number;
12
+ }
13
+ /**
14
+ * Starts playing the tone on the given source.
15
+ *
16
+ * Keep the returned stop function for as long as the bot stays in the room:
17
+ * stopping mid-flight leaves the peer with silence, not with an error — which
18
+ * is exactly what a bot that stops speaking should do.
19
+ *
20
+ * @param options Tone parameters; every field has a sensible default.
21
+ * @returns A function that stops the tone and clears its timer.
22
+ *
23
+ * @example
24
+ * ```ts
25
+ * const fonte = transporte.criarFonteDeAudio();
26
+ * const parar = tocarTom({ fonte, frequencia: 440, amplitude: 0.15 });
27
+ * // …later, on shutdown:
28
+ * parar();
29
+ * ```
30
+ */
31
+ export declare function tocarTom({ fonte, frequencia, amplitude, sampleRate, }: OpcoesDoTom): () => void;
32
+ //# sourceMappingURL=audio.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"audio.d.ts","sourceRoot":"","sources":["../../src/audio.ts"],"names":[],"mappings":"AAMA,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,UAAU,CAAC;AAmB7C,mEAAmE;AACnE,MAAM,WAAW,WAAW;IAC1B,+DAA+D;IAC/D,KAAK,EAAE,YAAY,CAAC;IACpB,yCAAyC;IACzC,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,0DAA0D;IAC1D,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,mDAAmD;IACnD,UAAU,CAAC,EAAE,MAAM,CAAC;CACrB;AAED;;;;;;;;;;;;;;;;;GAiBG;AACH,wBAAgB,QAAQ,CAAC,EACvB,KAAK,EACL,UAAgB,EAChB,SAAe,EACf,UAAmB,GACpB,EAAE,WAAW,GAAG,MAAM,IAAI,CA2B1B"}
@@ -0,0 +1,47 @@
1
+ /**
2
+ * Starts playing the tone on the given source.
3
+ *
4
+ * Keep the returned stop function for as long as the bot stays in the room:
5
+ * stopping mid-flight leaves the peer with silence, not with an error — which
6
+ * is exactly what a bot that stops speaking should do.
7
+ *
8
+ * @param options Tone parameters; every field has a sensible default.
9
+ * @returns A function that stops the tone and clears its timer.
10
+ *
11
+ * @example
12
+ * ```ts
13
+ * const fonte = transporte.criarFonteDeAudio();
14
+ * const parar = tocarTom({ fonte, frequencia: 440, amplitude: 0.15 });
15
+ * // …later, on shutdown:
16
+ * parar();
17
+ * ```
18
+ */
19
+ export function tocarTom({ fonte, frequencia = 440, amplitude = 0.2, sampleRate = 48_000, }) {
20
+ const comDados = fonte;
21
+ // 10 ms per block: it is the frame size of wrtc's RTCAudioSource.
22
+ const quadros = Math.round(sampleRate / 100);
23
+ const passo = (2 * Math.PI * frequencia) / sampleRate;
24
+ const limite = Math.max(0, Math.min(1, amplitude)) * 0x7fff;
25
+ let fase = 0;
26
+ const timer = setInterval(() => {
27
+ const amostras = new Int16Array(quadros);
28
+ for (let i = 0; i < quadros; i += 1) {
29
+ amostras[i] = Math.round(Math.sin(fase) * limite);
30
+ fase += passo;
31
+ if (fase > 2 * Math.PI)
32
+ fase -= 2 * Math.PI;
33
+ }
34
+ comDados.onData({
35
+ samples: amostras,
36
+ sampleRate,
37
+ bitsPerSample: 16,
38
+ channelCount: 1,
39
+ numberOfFrames: quadros,
40
+ });
41
+ }, 10);
42
+ // Without `unref` the process would not exit while the tone plays — and the
43
+ // bot must be able to leave the room and still shut down cleanly.
44
+ timer.unref?.();
45
+ return () => clearInterval(timer);
46
+ }
47
+ //# sourceMappingURL=audio.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"audio.js","sourceRoot":"","sources":["../../src/audio.ts"],"names":[],"mappings":"AAqCA;;;;;;;;;;;;;;;;;GAiBG;AACH,MAAM,UAAU,QAAQ,CAAC,EACvB,KAAK,EACL,UAAU,GAAG,GAAG,EAChB,SAAS,GAAG,GAAG,EACf,UAAU,GAAG,MAAM,GACP;IACZ,MAAM,QAAQ,GAAG,KAAsB,CAAC;IACxC,kEAAkE;IAClE,MAAM,OAAO,GAAG,IAAI,CAAC,KAAK,CAAC,UAAU,GAAG,GAAG,CAAC,CAAC;IAC7C,MAAM,KAAK,GAAG,CAAC,CAAC,GAAG,IAAI,CAAC,EAAE,GAAG,UAAU,CAAC,GAAG,UAAU,CAAC;IACtD,MAAM,MAAM,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,SAAS,CAAC,CAAC,GAAG,MAAM,CAAC;IAC5D,IAAI,IAAI,GAAG,CAAC,CAAC;IAEb,MAAM,KAAK,GAAG,WAAW,CAAC,GAAG,EAAE;QAC7B,MAAM,QAAQ,GAAG,IAAI,UAAU,CAAC,OAAO,CAAC,CAAC;QACzC,KAAK,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,GAAG,OAAO,EAAE,CAAC,IAAI,CAAC,EAAE,CAAC;YACpC,QAAQ,CAAC,CAAC,CAAC,GAAG,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC,GAAG,CAAC,IAAI,CAAC,GAAG,MAAM,CAAC,CAAC;YAClD,IAAI,IAAI,KAAK,CAAC;YACd,IAAI,IAAI,GAAG,CAAC,GAAG,IAAI,CAAC,EAAE;gBAAE,IAAI,IAAI,CAAC,GAAG,IAAI,CAAC,EAAE,CAAC;QAC9C,CAAC;QACD,QAAQ,CAAC,MAAM,CAAC;YACd,OAAO,EAAE,QAAQ;YACjB,UAAU;YACV,aAAa,EAAE,EAAE;YACjB,YAAY,EAAE,CAAC;YACf,cAAc,EAAE,OAAO;SACxB,CAAC,CAAC;IACL,CAAC,EAAE,EAAE,CAAC,CAAC;IACP,4EAA4E;IAC5E,kEAAkE;IAClE,KAAK,CAAC,KAAK,EAAE,EAAE,CAAC;IAChB,OAAO,GAAG,EAAE,CAAC,aAAa,CAAC,KAAK,CAAC,CAAC;AACpC,CAAC"}
@@ -0,0 +1,213 @@
1
+ import { ErroDaApi } from "./http.js";
2
+ import { type EstadoDoGateway } from "./gateway.js";
3
+ import type { CanalDeTexto, Descoberta, ServidorIce, Eventos, Intencao, Mensagem } from "./tipos.js";
4
+ /** Everything needed to build a {@link Bot}. */
5
+ export interface OpcoesDoBot {
6
+ /** Bot token (`vtb_…`), copied from the admin panel (Bots tab). */
7
+ token: string;
8
+ /** Server base URL. Default: `http://localhost:8080`. */
9
+ baseUrl?: string;
10
+ /** Intents this process wants; the server refuses whatever the panel did not grant. */
11
+ intents?: Intencao[];
12
+ /** Diagnostics: one line per state change. */
13
+ log?: (mensagem: string) => void;
14
+ }
15
+ /** What a command handler receives on every invocation. */
16
+ export interface ContextoDoComando {
17
+ /** The message that triggered the command. */
18
+ mensagem: Mensagem;
19
+ /** The channel where the command was typed, with its settings. */
20
+ canal: CanalDeTexto;
21
+ /** `!tocar a.mp3` → `["a.mp3"]` (already split on whitespace). */
22
+ args: string[];
23
+ /** Everything typed after the command name, as-is. */
24
+ resto: string;
25
+ /** Replies in the same channel. */
26
+ responder(texto: string): Promise<Mensagem>;
27
+ /** Deletes the triggering message — only works when the bot wrote it. */
28
+ apagar(): Promise<void>;
29
+ }
30
+ /** Handler signature for one gateway event. */
31
+ type Ouvinte<K extends keyof Eventos> = (dados: Eventos[K]) => void | Promise<void>;
32
+ /**
33
+ * A Vértice bot.
34
+ *
35
+ * Create one, register listeners with {@link on} and commands with
36
+ * {@link command}, then call {@link start}. Sessions, heartbeats, `resume` and
37
+ * reconnection are handled internally, so the author only has to react to
38
+ * events.
39
+ *
40
+ * @example
41
+ * ```ts
42
+ * const bot = new Bot({ token: process.env.VERTICE_BOT_TOKEN! });
43
+ *
44
+ * bot.command("ping", { descricao: "responde pong" }, async ({ responder }) => {
45
+ * await responder("pong");
46
+ * });
47
+ *
48
+ * await bot.start();
49
+ * ```
50
+ */
51
+ export declare class Bot {
52
+ #private;
53
+ /** @param opcoes Token, base URL and the intents this process wants. */
54
+ constructor(opcoes: OpcoesDoBot);
55
+ /** Identity the server assigned, or `null` before {@link start}. */
56
+ get bot(): Descoberta["bot"] | null;
57
+ /** Channels granted to the bot, or `null` before {@link start}. */
58
+ get canais(): Descoberta["canais"] | null;
59
+ /** ICE servers from discovery (the bot's voice uses the same ones). */
60
+ get iceServers(): ServidorIce[];
61
+ /** Current gateway state, or `"parado"` before {@link start} and after {@link stop}. */
62
+ get estado(): EstadoDoGateway | "parado";
63
+ /**
64
+ * Registers a listener for every gateway state change.
65
+ *
66
+ * Voice uses it to leave the room when the connection drops: `resume` brings
67
+ * the events back, but not the seat in the voice room.
68
+ *
69
+ * @param ouvinte Called with the new state.
70
+ * @returns This bot, for chaining.
71
+ */
72
+ aoMudarEstado(ouvinte: (estado: EstadoDoGateway) => void): this;
73
+ /** Last connection error, for callers that want to show it in a `/status` command. */
74
+ get ultimoErro(): Error | null;
75
+ /**
76
+ * Discovers what the bot may do, opens a session and connects the gateway.
77
+ *
78
+ * @returns This bot, once the gateway reports `ready`.
79
+ * @throws {ErroDaApi} When discovery or session creation fails.
80
+ * @throws {Error} When the server refuses the bot.
81
+ */
82
+ start(): Promise<this>;
83
+ /**
84
+ * Sends a raw gateway action (voice uses it to join, leave and signal).
85
+ *
86
+ * @param tipo Action name understood by the server.
87
+ * @param dados Action payload.
88
+ * @throws {Error} When `start()` has not been called yet.
89
+ */
90
+ agir(tipo: string, dados?: Record<string, unknown>): void;
91
+ /** Closes the gateway for good and forgets the session. */
92
+ stop(): Promise<void>;
93
+ /**
94
+ * Subscribes to a gateway event (`message.created`, `voice.joined`, …).
95
+ *
96
+ * @param nome Event name.
97
+ * @param ouvinte Handler; it may be async. Failures are logged, never thrown.
98
+ * @returns This bot, for chaining.
99
+ */
100
+ on<K extends keyof Eventos>(nome: K, ouvinte: Ouvinte<K>): this;
101
+ /**
102
+ * Removes a listener previously registered with {@link on}.
103
+ *
104
+ * @param nome Event name.
105
+ * @param ouvinte The exact handler reference that was registered.
106
+ * @returns This bot, for chaining.
107
+ */
108
+ off<K extends keyof Eventos>(nome: K, ouvinte: Ouvinte<K>): this;
109
+ /**
110
+ * Registers a command.
111
+ *
112
+ * The channel prefix (`!`) belongs to the server: here the name is just
113
+ * `tocar`. Without `canais`, the command works in every channel where the bot
114
+ * may speak. Every registered command is announced to the client's
115
+ * autocomplete, including ones registered after `start()`.
116
+ *
117
+ * @param nome Command name; a leading `!` or `/` is stripped.
118
+ * @param opcoesOuFn Either the options object or the handler itself.
119
+ * @param talvezFn Handler, when the second argument carries the options.
120
+ * @returns This bot, for chaining.
121
+ * @throws {Error} When no handler is provided.
122
+ *
123
+ * @example
124
+ * ```ts
125
+ * bot.command("ping", async ({ responder }) => {
126
+ * await responder("pong");
127
+ * });
128
+ *
129
+ * bot.command("eco", { descricao: "repete o texto" }, async ({ resto, responder }) => {
130
+ * await responder(resto);
131
+ * });
132
+ * ```
133
+ */
134
+ command(nome: string, opcoesOuFn: {
135
+ descricao?: string;
136
+ canais?: string[];
137
+ } | ((contexto: ContextoDoComando) => void | Promise<void>), talvezFn?: (contexto: ContextoDoComando) => void | Promise<void>): this;
138
+ /** Registered commands, in registration order (handy in a `!help` command). */
139
+ get comandos(): {
140
+ nome: string;
141
+ descricao?: string;
142
+ }[];
143
+ /**
144
+ * Sends a text message.
145
+ *
146
+ * It goes over HTTP on purpose: the response carries the created item (id,
147
+ * timestamp), and the gateway delivers `message.created` to everyone anyway.
148
+ *
149
+ * @param canal Channel code (case-insensitive; uppercased before sending).
150
+ * @param texto Message content.
151
+ * @returns The message the server created.
152
+ * @throws {ErroDaApi} When the bot cannot post in the channel.
153
+ */
154
+ enviar(canal: string, texto: string): Promise<Mensagem>;
155
+ /**
156
+ * Sends audio as a **voice message** — the item the client renders as a
157
+ * "voice message" and plays inline.
158
+ *
159
+ * @param canal Channel code.
160
+ * @param audio The audio bytes (WAV by default; see `wavDeTom`).
161
+ * @param opcoes File name and MIME type; defaults to `recado.wav` / `audio/wav`.
162
+ * @returns The message the server created.
163
+ * @throws {ErroDaApi} When the upload fails.
164
+ */
165
+ enviarVoz(canal: string, audio: Uint8Array, opcoes?: {
166
+ nome?: string;
167
+ mime?: string;
168
+ }): Promise<Mensagem>;
169
+ /**
170
+ * Sends any other file (image, PDF, audio as a regular attachment).
171
+ *
172
+ * @param canal Channel code.
173
+ * @param conteudo File bytes.
174
+ * @param opcoes File name and MIME type; defaults to `arquivo` /
175
+ * `application/octet-stream`.
176
+ * @returns The message the server created.
177
+ * @throws {ErroDaApi} When the upload fails.
178
+ */
179
+ enviarArquivo(canal: string, conteudo: Uint8Array, opcoes?: {
180
+ nome?: string;
181
+ mime?: string;
182
+ }): Promise<Mensagem>;
183
+ /**
184
+ * Reads a page of history (100 items; `antesDe` pages backwards).
185
+ *
186
+ * @param canal Channel code.
187
+ * @param antesDe Timestamp cursor: returns messages older than this one.
188
+ * @returns The page, plus `temMais` telling whether another page exists.
189
+ * @throws {ErroDaApi} When the bot cannot read the channel.
190
+ */
191
+ historico(canal: string, antesDe?: number): Promise<{
192
+ sala: string;
193
+ mensagens: Mensagem[];
194
+ temMais: boolean;
195
+ }>;
196
+ /**
197
+ * Deletes a message the bot wrote.
198
+ *
199
+ * @param canal Channel code.
200
+ * @param id Message id.
201
+ * @throws {ErroDaApi} When the message is not the bot's or is already gone.
202
+ */
203
+ apagar(canal: string, id: string): Promise<void>;
204
+ /**
205
+ * Re-runs only the discovery step (e.g. after changing channels in the panel).
206
+ *
207
+ * @returns The fresh discovery document.
208
+ * @throws {ErroDaApi} When the token is rejected.
209
+ */
210
+ recarregar(): Promise<Descoberta>;
211
+ }
212
+ export { ErroDaApi };
213
+ //# sourceMappingURL=cliente.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cliente.d.ts","sourceRoot":"","sources":["../../src/cliente.ts"],"names":[],"mappings":"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"}