Note operative Osservatorio

Hy4 preview di Tencent: il default del ragionamento si capovolge, in silenzio

7 min di lettura

Due fanali di segnalamento ferroviario identici, montati su due bracci curvi che escono dallo stesso palo e orientati in direzioni diverse, fotografia in bianco e nero contro un cielo nuvoloso
Stesso fanale, stesso braccio: soltanto l’angolazione dice dove punta ciascuno, e da terra non si vede finché non ci si passa sotto.

Il 27 agosto 2026, alle 08:52:40 UTC — campo createdAt dell’API di Hugging Face — Tencent ha pubblicato Hy4 preview: 770 miliardi di parametri totali, mixture-of-experts, licenza Apache 2.0. È il successore di Hy3 preview, in esercizio da aprile e ancora vivo: il comunicato Tencent datato 28 agosto annuncia che l’accesso gratuito a Hy3 resta aperto fino al 30 settembre. Due generazioni della stessa famiglia, stesso client OpenAI-compatibile, in produzione nello stesso mese. Abbiamo scaricato il chat template di entrambe — il file che traduce la conversazione in testo prima che il motore generi — per capire cosa cambia per chi sposta un’integrazione dall’una all’altra senza toccare il codice. Cambia il comportamento di default a ogni chiamata, e nessun errore lo segnala.

I fatti, in ordine

  • Hy4 preview: spazio tencent/Hy4-preview, createdAt 2026-08-27T08:52:40Z. Al momento della verifica, il 3 settembre 2026, il repository segna 3.516 download e 399 like. Licenza Apache 2.0, dichiarata nei tag e confermata dal file LICENSE: testo standard, copyright Tencent 2026, nessuna clausola aggiuntiva oltre l’attribuzione richiesta dalla licenza stessa.
  • Hy3 preview, il predecessore: createdAt 2026-04-13T06:07:57Z, licenza other — non Apache, un testo proprio di Tencent. Il comunicato dell’azienda, datato 28 agosto, dichiara: «Free access to Hy3 on both platforms has also been extended until September 30.», l’accesso gratuito a Hy3 su entrambe le piattaforme è stato inoltre esteso fino al 30 settembre: le due generazioni restano in esercizio in parallelo.
  • Architettura: 78 strati, 256 esperti instradati più uno condiviso, otto attivi per token, attenzione sparsa ispirata — dichiara la scheda — a DeepSeek e GLM. Non è il tema di questa nota: conta come il modello decide se ragionare prima di rispondere, non quanti parametri ha.
  • Il meccanismo: entrambi i chat_template.jinja — il file che ogni motore di inferenza applica prima di generare — leggono un parametro chiamato reasoning_effort. A high la risposta comincia con un blocco di pensiero esteso, fra i tag <think:opensource> e </think:opensource>; a no_think quel blocco resta vuoto e la risposta arriva diretta.

Il default che si è capovolto

La scheda di Hy4 preview è onesta, ma solo in un punto della pagina, in prosa, sotto la sezione Quickstart: «Defaults to “high” (deep chain-of-thought), which suits complex tasks such as math, coding, and reasoning», per difetto è impostato su “high” (catena di pensiero profonda), adatto a compiti complessi come matematica, programmazione e ragionamento. Quello che nessuna delle due schede scrive è che si tratta di un’inversione rispetto al predecessore, non di una scelta isolata.

Il chat_template.jinja di Hy3 preview, alla riga 36, dice: se reasoning_effort non è definito, o non è fra i tre valori ammessi, il template lo imposta a no_think — risposta diretta. È il comportamento che si ottiene non passando affatto il parametro: solo i messaggi, nient’altro. Il file equivalente di Hy4 preview cambia proprio quella riga: alle righe 32-33, se reasoning_effort non è definito, il template lo imposta a high — ragionamento esteso. Stessa condizione del codice sorgente, not reasoning_effort is defined, esito opposto.

La prova più diretta è nel codice che le due schede pubblicano come primo esempio d’uso. Il quickstart di Hy3 preview, riga 172, passa esplicitamente extra_body={"chat_template_kwargs": {"reasoning_effort": "no_think"}}, con un commento sopra che recita «(default, direct response)», (per difetto, risposta diretta): chi copiava quel blocco otteneva la risposta diretta due volte, per il parametro esplicito e per il default che lo confermava. Il quickstart di Hy4 preview, righe 145-152, ha lo stesso identico scheletro — stesso client, stesso metodo, gli stessi temperature=0.9 e top_p=1.0 — ma senza extra_body, senza chat_template_kwargs, senza traccia di reasoning_effort. Chi copia questo blocco oggi, come lo copiava un mese fa per Hy3, ottiene il comportamento opposto: non perché il codice sia sbagliato, ma perché il default a cui si affida in silenzio è cambiato sotto di lui, in un file che non fa parte del suo repository e che quasi nessuno legge prima di aggiornare l’endpoint.

Un secondo interruttore, fuori da entrambe le schede

Leggendo oltre la riga del default, il template di Hy4 preview contiene una condizione che non compare in nessuna scheda, in nessuna delle due lingue in cui Tencent le pubblica, né nella pagina delle ricette vLLM dedicata al modello — verificata direttamente. La scheda cinese, README_CN.md, nomina reasoning_effort una volta sola, per dichiarare lo stesso default high, e fallback_strategy non compare in nessuna delle sue 223 righe. Alle righe 42-45: se un campo chiamato fallback_strategy è definito e vale reasoning_toolcall_retry, il template forza reasoning_effort a high — anche sopra un no_think esplicito — e nello stesso ramo imposta add_generation_prompt a false, sopprimendo il marcatore di nuovo turno che aggiungerebbe altrimenti.

Non è un residuo dimenticato in un file isolato. Il checkpoint FP8 dello stesso modello — quello che la scheda raccomanda per la produzione — risulta creato, secondo l’API, alle 08:57:54 UTC dello stesso giorno, cinque minuti dopo il bf16. Il suo chat_template.jinja è quasi identico al principale, con una sola riga diversa: proprio quella che gestisce fallback_strategy, estesa per tenere aperto l’ultimo turno dell’assistente quando quel valore è impostato. Chi mantiene il file lo ha adattato apposta anche nella variante quantizzata: non è una svista di copia-incolla. In Hy3 preview questo campo non esiste, in nessuna riga.

Quello che si rompe ad alta voce, per contrasto

Non tutto quello che cambia fra le due generazioni resta silenzioso. Hy3 preview accettava tre valori per reasoning_effort: high, low, no_think. Hy4 ne accetta due: chi passa low — valido ieri — fa scattare, alle righe 34-39, un’eccezione con il messaggio «reasoning_effort error : low, should be no_think/high», errore su reasoning_effort: low, dovrebbe essere no_think/high, composto dal template stesso. Come il server la restituisca al chiamante non l’abbiamo verificato in esecuzione, ma la differenza è scritta nel file: un valore non ammesso interrompe la generazione, un valore assente no — chi ha scritto il template distingue i due casi, e sceglie quale dei due segnalare.

Quello che non abbiamo verificato

Non abbiamo eseguito né Hy3 né Hy4 preview: la lettura è sui file dei repository, non su un’inferenza reale, e non sappiamo con quale messaggio esatto vLLM o SGLang restituiscano l’eccezione del template al chiamante. Non sappiamo quale componente della pipeline di serving imposti fallback_strategy: reasoning_toolcall_retry in produzione, né con quale frequenza: la ricerca nel codice su GitHub via API ha risposto 401, un token che non avevamo, e la ricerca sul web non ha restituito documentazione pubblica del campo. Non abbiamo misurato il costo in token del blocco di pensiero esteso su un caso reale: sappiamo che il default lo attiva, non quanto pesi sulla bolletta di chi lo eredita senza saperlo.

Cosa fare, in pratica

  • Prima di spostare una chiamata da un checkpoint a un altro della stessa famiglia, diff-ate i due chat_template.jinja: file pubblici di poche centinaia di righe, che dicono più della prosa della scheda.
  • Passate sempre reasoning_effort in modo esplicito: affidarsi al default significa affidarsi a una riga che il fornitore può cambiare senza obbligo di segnalarlo.
  • Cercate campi non documentati prima della produzione: un grep sulle variabili lette con is defined trova in un minuto quello che nessuna scheda elenca.
  • Se un vostro layer di retry o di orchestrazione tool-calling aggiunge parametri alla chiamata, verificate che nessuno sovrascriva una scelta esplicita fatta a monte.
  • Registrate checkpoint e versione del chat template in esercizio: un aggiornamento silenzioso del secondo cambia il comportamento del primo senza toccare un peso.

Il salto dichiarato da Hy3 a Hy4 preview è sui benchmark. Il salto che conta per chi lo mette in esercizio è in un file di poche righe che nessuna scheda descrive per intero, e che decide se ogni risposta comincia con un pensiero o con una parola.

State migrando un’integrazione da un modello a pesi aperti al suo successore, o valutando quale usare in produzione? Mezz’ora con un nostro esperto: leggiamo insieme chat template, config e comandi di avvio prima che il default lo scopra un cliente.

Fonti