Co to je
Voya je plánovač cest, kterému stačí věta. Napíšeš, kam a na jak dlouho jedeš, a jazykový model z toho udělá itinerář rozepsaný po dnech: každá zastávka má čas, délku, kategorii, popis a adresu. Rozpis není hotová věc, kterou musíš vzít, jak je — dá se upravovat a přerovnávat. Vedle něj je mapa, takže je hned vidět, jestli den zbytečně nepřejíždí přes celé město. Hotovou cestu jde zveřejnit; na /explore je pak přehled toho, co nasdíleli ostatní, s filtry podle délky, rozpočtu a oblíbenosti, a cizí cestu jde jedním kliknutím zkopírovat do vlastních.
Proč jsem to dělal
Plánování výletu se rozpadá na dvě různé práce: vymyslet, co se dá stihnout, a udělat z toho rozpis, podle kterého se dá ráno vstát a jít. Jazykový model zvládne první z nich za pár vteřin — a přesně tam je háček. Model umí napsat věrohodně znějící adresu místa, které neexistuje, nebo posadit kavárnu o dvě města vedle. Rozpis, kterému se nedá věřit v tom, kde ta místa jsou, je k ničemu. Celé to navíc mělo běžet na bezplatných tarifech, takže se problém nedal vyřešit tím, že se na něj koupí lepší služba.
Jak jsem to stavěl
Nejdřív specifikace, pak kód. Než jsem napsal první komponentu, bylo hotové zadání s uživatelskými příběhy, architektura, datový model, kontrakt každého API a očíslovaný seznam úkolů, podle kterého se stavělo v pořadí. Jádrem je jedno schéma v Zodu, které sdílí výstup modelu, API vrstva i databáze — takže si tři části aplikace nemůžou představovat stejná data jinak. Úkol je hotový, až projde kontrola typů, ESLint i produkční build; nic mezi tím se za hotové nepočítá.
Co je uvnitř
Model je Gemini 2.5 Flash-Lite, se záložním Groqem, když první neodpoví. Jeho výstup je strukturovaný JSON, který projde Zodem dřív, než se ho něco dotkne — parsuj, nedůvěřuj. Souřadnice od modelu se zahazují: každé místo se na serveru geokóduje přes MapTiler a okolní body zájmu se dohledávají v Overpassu nad OpenStreetMap. Mapa je MapLibre GL. Do prohlížeče se pouští jediný klíč, ten na dlaždice, a je omezený na doménu — volání modelu i geokódování běží výhradně na serveru. Data jsou v Postgresu na Neonu přes Prismu, přihlašuje se přes Auth.js a Google. Aplikace je psaná serverově: výchozí jsou serverové komponenty a `use client` dostane jen to, co bez interaktivity nefunguje — mapa, přerovnávání zastávek, formuláře. Vzhled drží vlastní návrhový systém Luminous Travel: barvy, velikosti písma i zaoblení jsou tokeny v Tailwindu v4 a v žádné komponentě není napsaná konkrétní barva. U každého přetahování je i klávesová varianta.


Celá stránka
Rám se roluje — je to jeden snímek shora dolů.
