Gli SDK ufficiali racchiudono l’API REST per il codice server e gli script. Una sola chiamata trascrive un file: carica la registrazione, attende il job e restituisce la trascrizione. Nel frattempo l’SDK controlla il file prima che vengano trattenuti dei minuti, ripete ciò che si può ripetere senza rischi, mantiene attivo un caricamento lungo e inserisce una chiave di idempotenza in ogni caricamento e acquisto, così un nuovo tentativo non addebita mai due volte. La CLI è costruita sull’SDK TypeScript e fa lo stesso da terminale.
Pacchetti
| Linguaggio | Pacchetto | Registro | Sorgente |
|---|---|---|---|
| TypeScript | @hushscript/sdk | npm: www.npmjs.com/package/@hushscript/sdk | github.com/Hushscript/hushscript-sdk-typescript |
| Python | hushscript | PyPI: pypi.org/project/hushscript | github.com/Hushscript/hushscript-sdk-python |
| Go | github.com/Hushscript/hushscript-sdk-go | pkg.go.dev: pkg.go.dev/github.com/Hushscript/hushscript-sdk-go | github.com/Hushscript/hushscript-sdk-go |
| PHP | hushscript/sdk | Packagist: packagist.org/packages/hushscript/sdk | github.com/Hushscript/hushscript-sdk-php |
| CLI | @hushscript/cli | npm: www.npmjs.com/package/@hushscript/cli | github.com/Hushscript/hushscript-cli |
Versioni minime del runtime:
- TypeScript: Node 22 o successivo. Bun 1.2+ e Deno 2+ sono verificati solo per l’importazione del pacchetto, non per il comportamento HTTP.
- Python: 3.10 o successivo.
- Go: 1.25 o successivo.
- PHP: 8.2 o successivo, con
ext-jsoneext-mbstring;ext-curlper il caricamento simultaneo delle parti. - CLI: Node 22 o successivo.
Gli SDK sono pensati per server e script. L’API non accetta origini del
browser, e un token in un bundle per il browser è un token compromesso, quindi
l’SDK TypeScript si rifiuta di avviarsi dove esistono window e document.
Ottenere un token
Ogni SDK e la CLI si autenticano con un token di accesso personale. Creane uno
sotto Crea un nuovo token nella pagina MCP dell’account,
scegli gli scope che servono al tuo codice e decidi se può acquistare minuti.
Il token viene mostrato una sola volta e ha la forma
hsr1:<region>:pat.<id>.<secret>. Gli scope e il funzionamento di un token
sono nella pagina dell’API.
Gli SDK leggono il token da HUSHSCRIPT_TOKEN quando non ne passi uno:
export HUSHSCRIPT_TOKEN=hsr1:...
Un agente può anche aprire un proprio account, farlo pagare su una pagina di
checkout ospitata e ottenere il suo primo token da codice:
Hushscript.agent.signup() e Hushscript.agent.claim() in TypeScript,
Hushscript.agent_signup() e Hushscript.agent_claim() in Python, AgentSignup e AgentClaim in
Go, e Client::agentSignup() e Client::agentClaim() in PHP. Il flusso e le
sue regole sono in Uso automatizzato.
TypeScript
npm install @hushscript/sdk
import { writeFile } from "node:fs/promises";
import { Hushscript } from "@hushscript/sdk";
const hs = new Hushscript(); // reads HUSHSCRIPT_TOKEN
const transcript = await hs.transcribe("meeting.mp3");
console.log(transcript.text);
await writeFile("meeting.srt", transcript.toSRT());
transcribe() accetta un percorso, un Blob, un Uint8Array o un
ReadableStream<Uint8Array>. Uno stream richiede il suo size e il suo
durationSeconds esatti. hs.balance() restituisce i minuti che puoi
spendere, hs.transcripts.list() scorre le trascrizioni completate e
hs.buy("300min", { acknowledgeNoRefund: true }) acquista un pacchetto.
Ogni operazione /v1 è disponibile anche come hs.api, con gli stessi nuovi
tentativi, timeout e oscuramento.
Python
pip install hushscript
from pathlib import Path
from hushscript import Hushscript
with Hushscript() as hs: # reads HUSHSCRIPT_TOKEN
transcript = hs.transcribe("meeting.mp3")
print(transcript.text)
Path("meeting.srt").write_text(transcript.to_srt(), encoding="utf-8")
Ogni chiamata ha un gemello asyncio su AsyncHushscript con gli stessi nomi.
transcribe() accetta un percorso, bytes o un file object binario; un file
object che non supporta il seek richiede size e duration_seconds.
hs.balance(), hs.transcripts.list() e
hs.buy("300min", acknowledge_no_refund=True) coprono saldo, elenco delle
trascrizioni e acquisti.
Go
go get github.com/Hushscript/hushscript-sdk-go
package main
import (
"context"
"fmt"
"log"
"os"
hushscript "github.com/Hushscript/hushscript-sdk-go"
)
func main() {
client, err := hushscript.New() // reads HUSHSCRIPT_TOKEN
if err != nil {
log.Fatal(err)
}
transcript, err := client.Transcribe(context.Background(), "meeting.mp3", nil)
if err != nil {
log.Fatal(err)
}
fmt.Println(transcript.Text(nil))
if err := os.WriteFile("meeting.srt", []byte(transcript.SRT(nil)), 0o600); err != nil {
log.Fatal(err)
}
}
Transcribe accetta un percorso, TranscribeReader un io.ReaderAt con la
sua dimensione esatta, e TranscribeStream un lettore sequenziale con la sua
dimensione e DurationSeconds. client.Balance, client.Transcripts.List e
client.Buy coprono saldo, elenco delle trascrizioni e acquisti. Le opzioni
che possono essere attive, disattive o non impostate sono *bool, create con
hushscript.Bool.
PHP
composer require hushscript/sdk
<?php
require __DIR__ . '/vendor/autoload.php';
use Hushscript\Client;
$hs = new Client(); // reads HUSHSCRIPT_TOKEN
$transcript = $hs->transcribe('meeting.mp3');
echo $transcript->text();
file_put_contents('meeting.srt', $transcript->toSrt());
transcribe() accetta un percorso o uno stream aperto; uno stream che non
supporta il seek richiede le opzioni size e duration_seconds. Le opzioni
usano chiavi di array in snake_case e i risultati usano proprietà in
camelCase. $hs->balance(), $hs->transcripts()->list() e
$hs->buy('300min', true) coprono saldo, elenco delle trascrizioni e
acquisti. Per Laravel, collega un solo Client in un service provider ed
esegui le trascrizioni in un job in coda con un’opzione idempotency_key
stabile.
CLI
npm install --global @hushscript/cli
hushscript login
hushscript transcribe meeting.mp3 --format srt --out meeting.srt
La CLI prende il token da --token, poi da HUSHSCRIPT_TOKEN, poi da quello
salvato da hushscript login. login chiede il token senza mostrarlo a
schermo e lo conserva in un file leggibile solo dal tuo utente; hushscript logout lo elimina. In CI, preferisci la variabile d’ambiente.
| Comando | Cosa fa |
|---|---|
login |
Chiede un token e lo salva. |
logout |
Elimina il token salvato. |
balance |
Mostra i minuti che puoi spendere. |
transcribe <file> |
Carica una registrazione, attende e stampa la trascrizione. Flag: --language, --translate, --format srt|vtt|txt|json, --out, --key. |
resume <token> <file> |
Completa una trascrizione lasciata in sospeso da transcribe. |
transcripts |
Elenca le trascrizioni completate, dalla più recente. |
transcript <id> |
Stampa una trascrizione. |
jobs |
Elenca i job; --active per quelli non ancora terminati. |
packs |
Elenca i pacchetti di minuti acquistabili, con i prezzi. |
buy <pack> |
Acquista un pacchetto con la tua carta predefinita salvata. Flag: --yes, --key. |
--json stampa un solo documento JSON su stdout e nient’altro, e trasforma
stderr in JSON Lines. Il codice di uscita è 0 in caso di successo, 1 quando
l’API o l’SDK hanno segnalato un errore, 2 per un errore d’uso (non è stato
inviato nulla) e 130 quando l’esecuzione è stata interrotta.
File supportati
MP3, M4A, MP4 e MOV (si usa la traccia audio di un video), WAV, FLAC e OGG con Vorbis o Opus, da 15 secondi a 10 ore. Gli SDK verificano il formato dai byte del file e misurano la durata prima che vengano trattenuti dei minuti. Non convertono i contenuti multimediali, quindi converti prima qualsiasi altro formato:
ffmpeg -i input -vn -c:a libopus output.opus
Errori
Ogni errore generato da un SDK appartiene a una sola famiglia, quindi un solo
catch copre tutto: HushscriptError in TypeScript e Python,
*hushscript.Error in Go e HushscriptException in PHP. Un errore porta uno
slug code come insufficient_balance, il codice numerico, lo stato HTTP, un
messaggio, un hint che indica cosa fare dopo, i dettagli e retryAfter (in PHP lo slug è errorCode; in Python retryAfter
è retry_after).
import { HushscriptError, InsufficientBalanceError } from "@hushscript/sdk";
try {
await hs.transcribe("meeting.mp3");
} catch (error) {
if (error instanceof InsufficientBalanceError) console.log(error.hint);
else if (error instanceof HushscriptError) console.log(error.code, error.hint ?? error.message);
else throw error;
}
Un PreflightError significa che l’SDK ha rifiutato il file prima che venisse
trattenuto del credito. Stabilire se il saldo copre un file spetta al server:
un 402 arriva quando il caricamento viene creato, prima che venga inviata
qualsiasi parte.
Addebiti e nuovi tentativi
Ogni caricamento e ogni acquisto porta una chiave di idempotenza, e i nuovi tentativi la riutilizzano, quindi una chiamata ripetuta ripropone la prima invece di avviarne una seconda.
buy() addebita la tua carta predefinita salvata. Acquistare da codice è
disattivato finché tre interruttori non lo consentono: il token ha lo scope
billing, il token ha “Consenti a questo token di acquistare minuti”
attivato e “Consenti alle app connesse di acquistare minuti” è attivo per
l’account. Se ne manca uno, la chiamata fallisce con pat_scope_missing.
Mostra al tuo acquirente l’avviso di non rimborsabilità prima di chiamarla.
Un acquisto viene ripetuto al massimo una volta, dopo un errore di rete, un
502 o un 503, con la stessa chiave. Alcune risposte dimostrano che non è
stato addebitato nulla: un 400, 402, 404 o 422, e un 403 con codice 4021
(pat_purchase_requires_app, la carta è stata rifiutata o non può essere
addebitata senza di te) o 4023 (pat_purchase_requires_authentication, la
banca vuole confermare il pagamento). Dopo 4021 o 4023, acquista il pacchetto
nell’app. Qualsiasi altro errore dopo l’invio della richiesta, compresi un 401
o un 429, significa che la carta potrebbe essere stata addebitata. Quell’errore
porta la chiave di idempotenza: riprova con la stessa chiave e l’acquisto non
può mai avvenire due volte. In Python:
from hushscript import HushscriptError
try:
purchase = hs.buy("300min", acknowledge_no_refund=True)
except HushscriptError as error:
refused = error.status in {400, 402, 404, 422} or (
error.status == 403 and error.numeric_code in {4021, 4023}
)
if error.idempotency_key is None or refused:
raise # only these refusals charged nothing; any other failure keeps the key for a retry
purchase = hs.buy("300min", acknowledge_no_refund=True, idempotency_key=error.idempotency_key)
Un acquisto fallito prima dell’invio della richiesta non porta alcuna chiave:
non è stato addebitato nulla. Una chiave che passi tu stesso deve avere da 1 a
128 caratteri tra A-Za-z0-9_-; non riutilizzarla per un pacchetto diverso.
La CLI stampa la chiave quando un acquisto potrebbe essere stato inviato:
hushscript buy 300min --yes --key <key>
Token di ripresa
Una volta creato il job, un errore porta un token di ripresa accanto alla
chiave di idempotenza. Un’attesa che scade genera WaitTimeoutError con il
token, e il job continua a funzionare. Passa il token a resume() per
proseguire senza un secondo addebito: un job oltre il caricamento non
richiede il file, e uno ancora in caricamento prosegue con lo stesso file. In
PHP:
try {
$hs->transcribe($path, ['wait_timeout' => 60]);
} catch (\Hushscript\Exception\WaitTimeoutError $timeout) {
$transcript = $hs->resume($timeout->resumeToken, $path);
}
Nella CLI, premere Ctrl-C durante transcribe stampa il token di ripresa del
job e il comando che lo porta avanti:
hushscript resume <token> meeting.mp3 --format srt --out meeting.srt
Log e oscuramento
Gli SDK non inviano alcuna telemetria; l’intestazione User-Agent è l’unica
identificazione del client. I log sono disattivati per impostazione
predefinita. HUSHSCRIPT_LOG=debug scrive una riga per richiesta sullo
standard error con metodo, percorso, stato e tempi, e mai un’intestazione, un
corpo, un titolo o il testo di una trascrizione.
Il token viene oscurato in ogni errore, riga di log e forma stampata del
client. Nei messaggi di errore, negli hint e nelle cause, un URL mantiene
host e percorso ma la sua query string diventa ?[redacted], così un URL di
caricamento firmato non viene mai stampato. I risultati che ti consegnano un
segreto, come un segreto di attivazione o un nuovo token, lo mantengono
leggibile come campo ma mostrano [redacted] quando vengono stampati; un
export JSON è tuo e contiene il valore. La CLI ripulisce da stderr ogni token
che conosce; i suoi risultati su stdout sono il tuo output e non vengono
ripuliti.
Configurazione
| Impostazione | Variabile d’ambiente | Predefinito |
|---|---|---|
| Token | HUSHSCRIPT_TOKEN |
nessuno |
| URL di base | HUSHSCRIPT_BASE_URL |
https://api.hushscript.com |
| Livello di log | HUSHSCRIPT_LOG |
off |
| Timeout della richiesta | nessuna | 60 secondi |
| Nuovi tentativi | nessuna | 3 |
Un’opzione passata nel codice ha la precedenza sulla sua variabile d’ambiente, e un valore vuoto vale come non impostato. I minuti provengono dallo stesso saldo dell’app; pacchetti e prezzi sono nella pagina dei prezzi.