Mia moglie voleva Dior. Ho speso 600 $ su Claude Code per fare vibe-coding di un database da 2 milioni di righe.
Mia moglie e io siamo sposati da dieci anni, e lei voleva una borsa Dior per il nostro anniversario.
Invece di comprare qualcosa — perché ero completamente assorbito da un esperimento di IA — ho passato l’intera vacanza chiuso nel mio studio, destreggiandomi tra tre abbonamenti Claude Code da 200 dollari al mese, cercando di convincere un LLM a effettuare la cross-compilazione di un database distribuito in C++ da 2 milioni di righe.
E probabilmente potete immaginare cosa mi sia successo dopo. 😂
Col senno di poi, questa non è stata un’allocazione ottimale delle risorse.
Quindi quel weekend ho imparato due lezioni.
Primo: ascolta tua moglie. “Moglie felice, vita felice” non è solo uno slogan. È un principio di stabilità dei sistemi.
Secondo: l’IA sembra magica su compiti piccoli e ben delimitati. Si comporta in modo molto diverso quando la indirizzi verso una vera infrastruttura distribuita.
Questo post parla della seconda lezione.
Contesto
Sono il maintainer e core contributor di Milvus, il database vettoriale open-source più popolare con oltre 42K stelle su GitHub al momento della scrittura (~2 milioni di righe di C++, Go e Python). Il sistema è completamente distribuito: nodi proxy, nodi di query, nodi dati e nodi indice si coordinano tutti tramite code di messaggi. La mia area è il livello di storage e indicizzazione.
Usavo Claude Code da qualche mese ed ero sinceramente colpito. Ha completato tutte le funzionalità mancanti di un’intera CLI per 20 dollari in token. Ha quintuplicato in un giorno le prestazioni di un percorso critico di query, il tipo di ottimizzazione per cui mi sarebbe servita una settimana solo per capire il codice abbastanza da poterlo toccare. Sembrava di avere un junior engineer competente che non dormiva mai e non fatturava a ore.
Ho deciso di dargli un problema reale: la compilazione cross-platform.
La lezione da 600 dollari
Per anni, nessuno nel team di Milvus avrebbe toccato la compilazione cross-platform. Il sistema di build è un mix di Go, C++ e Rust tenuto insieme da anni accumulati di patch Conan e CMake che nessuno voleva rivedere. Farlo girare su Linux è già miserabile. Windows e il macOS moderno erano un incubo tale da compilare che il team li trattava come un problema di qualcun altro.
Ho pensato che ora avevo Claude Code. Potevo gestirla.
All’inizio, sembrava che avessi ragione. Windows compilava, e ho inviato la patch, pensando che la parte difficile fosse finita.
Poi Linux ha fallito. Ho sistemato Linux e Mac ha fallito. Ho sistemato Mac, e l’ambiente GPU ha fallito. Ogni correzione introduceva due nuovi problemi su una piattaforma diversa, e le patch hanno iniziato ad accumularsi. Alla fine, avevo una patch da 1000 file e ~100k righe che toccava configurazioni Conan, script CMake, shim di compatibilità C++ e cose che non riconoscevo.
La parte esasperante non erano i bug; era il ciclo. Continuavo a dire a Claude: "Niente fix raffazzonati", "dammi la soluzione pulita." Obbediva ogni singola volta, generando patch che sembravano più pulite. Poi ogni patch pulita rompeva altre tre piattaforme, e il ciclo ricominciava. Se guardaste il mio .claude/settings.local.json, trovereste 147 regole di autorizzazione approvate manualmente. Ognuna è un timestamp di me che pensavo: "Questa volta funzionerà."
Ho speso 600 dollari per il piano Max e bruciato un’intera vacanza, e tutto ciò che avevo era una pila di comandi git reset --hard.
Sono rimasto lì a fissare il terminale, chiedendomi se tutta questa storia fosse solo hype ben confezionato. Poi ho capito che il problema non era Claude. Era come dire a un dottorando di pubblicare un articolo su Nature senza specificare la domanda di ricerca. Gli avevo dato un problema senza mai definire cosa significasse davvero "risolto".
Cosa funziona davvero
Il fallimento non era dovuto all’intelligenza di Claude. Era un fallimento di processo. Così ho ricominciato con un processo diverso.
Vincoli prima del codice. Non "farlo compilare su Windows." I vincoli effettivi, scritti esplicitamente: tutte le piattaforme superano i loro unit test, la CI è verde ovunque, niente hack di piattaforma con #ifdef, niente shim attorno a dipendenze rotte. Questa è la parte difficile — richiede sapere che aspetto ha "fatto", il che richiede pensare attentamente prima di toccare qualsiasi cosa. Con infrastrutture complesse, la maggior parte del lavoro sta nel pensare.
Revisionare i test, non il codice. Scrivo casi di test (o faccio in modo che Claude li generi), ma revisiono i test, non l'implementazione. Questo test verifica che la recipe Conan si risolva correttamente su ARM? Copre la configurazione CMake in Docker? Posso valutarlo in pochi minuti. Non posso revisionare 10.000 righe di patch C++ cross-platform con alcuna fiducia, in nessuna quantità di tempo.
Bottom-up, un livello alla volta. Non lasciare che Claude modifichi 1000 file. Blocca prima le versioni delle dipendenze. Una volta verificati quei vincoli, passa alla configurazione CMake. Una volta che è stabile, al codice specifico per piattaforma. Ogni livello è abbastanza piccolo da poter essere verificato completamente prima di salire.
Ho rifatto da zero la build cross-platform usando questo approccio. Due giorni. Qualche decina di commit. Ognuno piccolo, ognuno con un test corrispondente. Niente hack con #ifdef — la correzione sottostante è stata aggiornare le recipe Conan e aumentare le versioni delle librerie di terze parti, sistemando la catena di dipendenze effettiva invece di metterci una pezza sopra.
Stesso compito. Esito completamente diverso.
L'intuizione sui test merita un punto a sé: in un sistema distribuito con una suite di test matura, i test sono la specifica. Se quei test di integrazione passano — tutti e 47 che erano diventati rossi durante il mio primo tentativo — allora i contratti seal/flush sono intatti, il replay del WAL è corretto e i query node possono ancora caricare segmenti con mmap senza corruzione. Non ho bisogno di leggere il C++ per saperlo.
Ho smesso di revisionare codice. Ho iniziato a revisionare test. Il codice è diventato un dettaglio implementativo.
Buttarci hardware
Una volta che il workflow era quello giusto, è apparso un nuovo collo di bottiglia: stavo lì seduto ad aspettare.
Una sessione di Claude Code che macina una codebase da 2M righe non è veloce. Ogni task richiede 20-30 minuti di tempo reale. Il collo di bottiglia non era l'intelligenza. Era il throughput.
Così ho detto a mia moglie che avevo bisogno di un server con una GPU per i miei “agenti AI.” Quella conversazione è andata più o meno come ci si aspetterebbe. L'ho comprato comunque — più un Mac Mini da affiancare al mio MacBook. Alla fine, avevo tre macchine e sei terminali, ciascuno con una sessione indipendente di Claude Code in esecuzione.
Ciò che fa funzionare questo è git worktree. Ogni sessione riceve il proprio task, branch e working directory, completamente isolati dagli altri. E poiché l'approccio constraints-first significa che ogni branch ha i propri criteri di accettazione, il parallelismo è banalmente sicuro: se i test di ogni branch passano indipendentemente, il merge è a basso rischio.
Per la build cross-platform, questo significava una sessione che risolveva le dipendenze Conan per Linux ARM, una che sistemava la configurazione CMake su macOS e una che gestiva la compatibilità Windows MSVC, tutte in esecuzione simultaneamente senza interferenze. Quello che prima era context-switching seriale tra piattaforme è diventato esecuzione parallela su più macchine.
Il pattern si generalizza al lavoro quotidiano. In un dato giorno, una sessione sta rifattorizzando lo scheduler di compaction, un'altra sta ottimizzando il percorso di ricerca HNSW e una terza sta scrivendo test di integrazione per un caso limite di streaming insert. Salto tra i terminali come un manager che controlla i riporti diretti, solo che questi riporti diretti non hanno mai bisogno di pause caffè e non hanno opinioni sulla pianificazione degli sprint.
La vera lezione è che l'infrastruttura di vibe coding è limitata dal compute, non dal talento. Il fattore limitante non è quanto sia intelligente l'AI; è quante istanze puoi eseguire in parallelo. Anthropic ha usato 16 istanze parallele di Claude per costruire un intero compilatore C, il che faceva sembrare modesti i miei sei terminali.
La cosa a cui continuo a tornare
L'AI risolve esattamente il problema che le metti davanti, niente di più. Se inquadri il problema nel modo sbagliato, ottieni una soluzione perfetta alla cosa sbagliata.
"Compiles on macOS 15" — risolto in un'ora. Ma quello è un ottimo locale. L'obiettivo reale era "compiles everywhere without hacks." Sono problemi diversi. L'AI non aveva modo di saperlo. Questa è interamente responsabilità dell'ingegnere.
Costruire per sé stessi con l'AI è incredibilmente facile — conosci la tua macchina, i tuoi casi limite, e "works for me" è un target di ottimizzazione raggiungibile. Costruire infrastruttura che funzioni per ogni utente, su ogni piattaforma, in ogni ambiente è fondamentalmente diverso. Quel divario è dove vive ancora l'ingegneria. Per il software infrastrutturale, quel divario è enorme.
I bug più difficili nel nostro sistema di produzione — quelli che hanno richiesto un revert dopo il merge — non sono stati individuati da nessun approccio di code review con AI che abbiamo provato. I bug erano sintatticamente corretti. Il problema era nelle assunzioni implicite dello sviluppatore, invisibili nel diff e assenti nel codice circostante. Il comportamento del sistema aveva senso solo se si aveva in mente un modello mentale di come tre componenti diversi avrebbero dovuto coordinarsi — un modello che esisteva solo nella testa di uno sviluppatore, mai scritto da nessuna parte.
Quelli richiedono ancora un essere umano che comprenda il sistema abbastanza bene da sapere quali domande fare.
I tre piani da $200 e una vacanza persa sono stati il miglior investimento che abbia fatto. Non perché mi abbiano insegnato come usare l'AI. Perché mi hanno insegnato come non usarla.
Gli strumenti sono davvero validi. Il pezzo mancante è sempre stato il workflow intorno a essi. Test prima del codice, vincoli prima dei test, e abbastanza hardware per far girare tutto in parallelo. È tutto qui.
I problemi che restano irrisolti
Dopo tutto — la patch fallita, i comandi di reset, i sei terminali in parallelo — il problema più difficile da risolvere è ancora quello umano.
Per ora, ho due grattacapi, e nessuno dei due ha una soluzione pulita.
Il primo: mia moglie. È arrivata alla vacanza con aspettative ragionevoli. Se n'è andata guardandomi fare git reset --hard sulla mia vita. Il budget per la borsa Dior è diventato una fattura del server. Lei, comprensibilmente, non è colpita dai miei risultati di build cross-platform. Devo ancora trovare un workflow per "come scusarsi per aver passato il proprio anniversario a fare lavoro sui sistemi distribuiti." Claude Code non è utile qui. Ho provato a chiedere. Ha suggerito fiori e un biglietto scritto a mano. Gli ho detto di essere più specifico. Ha generato dodici varianti di una lettera sentita con la voce di uno sviluppatore C++. Nessuna ha funzionato.
Se qualcuno ha risolto il problema di mantenere una relazione mentre fa vibe-coding durante una vacanza, sono apertissimo a suggerimenti di workflow. 😂
Il secondo: come scalare tutto questo oltre me. Tutto quanto sopra — l'approccio constraints-first, il parallelismo con git worktree, la disciplina di review test-first — è attualmente nella mia testa e nel mio setup locale. Portarlo nel workflow quotidiano di un team è più difficile di qualsiasi build cross-platform.
Questo è in parte un problema di tooling. Ma soprattutto è un problema di persone. Questo tipo di workflow richiede ingegneri a cui piaccia davvero capire come funzionano le cose — persone che scriveranno davvero prima il test, che trovano soddisfazione in un vincolo pulito e ben definito, e che non prenderanno scorciatoie per arrivare a "just make it pass." Questa combinazione è più rara di quanto dovrebbe essere.
Quindi sì — stiamo assumendo.
Se sei il tipo di ingegnere che legge un articolo sull'infrastructure vibe coding e inizia subito a formarsi opinioni forti su ciò che ho sbagliato, sei esattamente la persona con cui voglio parlare.
Milvus è un problema di sistemi distribuiti davvero difficile: storage engine, pipeline di indicizzazione, compaction, replica, recovery dai guasti — tutto sotto carico di produzione reale. Non stiamo costruendo demo. Stiamo costruendo infrastruttura da cui le persone dipendono.
Se risolvere problemi a quel livello ti sembra interessante, vieni a costruire con noi.
E al piano di recupero dell'anniversario ci penso io.
Puoi consultare le nostre posizioni aperte o contattarmi direttamente su LinkedIn.
E se non sei d’accordo con qualcosa in questo post, ancora meglio — sarò felice di discuterne con te.
Unisciti alla nostra community Slack o prenota una sessione di Milvus Office Hours — siamo sempre felici di parlare di sistemi distribuiti, infrastruttura AI o di dove pensi che ci sbagliamo.
Continua a leggere

How to Improve Retrieval Quality for Japanese Text with Sudachi, Milvus/Zilliz, and AWS Bedrock
Learn how Sudachi normalization and Milvus/Zilliz hybrid search improve Japanese RAG accuracy with BM25 + vector fusion, AWS Bedrock embeddings, and practical code examples.

Demystifying the Milvus Sizing Tool
Explore how to use the Sizing Tool to select the optimal configuration for your Milvus deployment.
Milvus/Zilliz + Surveillance: How Vector Databases Transform Multi-Camera Tracking
See how Milvus vector database enhances multi-camera tracking with similarity-based matching for better surveillance in retail, warehouses and transport hubs.



