Active
K39
A travel guide to Kaliningrad Oblast
Helps visitors choose places and plan a trip through a map, routes and destination pages.
I built the web app and its editorial workflow. Pages are server-rendered from PostgreSQL; AI agents have a separate draft-only access level without publishing rights.
Problem
A visitor needs to know where they can get in, when it is open, what it costs and how to get there. I want to gather this on one site where every place has its own page with sources, and to get visitors from search.
What was built
k39.online has place pages (forts, castles, beaches, resorts, food), a map, routes, collections and quests, a venue catalog with hours and prices, and site search. Editors work in an admin area; venue owners edit their listing in a cabinet. The first version in 2025 was a social product with follows and a feed. On 10 October 2026 I reset the repository into a content site, and it has had 263 commits since. Work is tracked in GitHub Issues, Cursor and Codex agents write the code, and decisions are recorded in ADRs.
Key decisions
All content in Postgres, admin inside the app
Place copy used to live in markdown and sync into the database, and the copies drifted. Now there is one database, and published pages are server-rendered, which SEO needs.
Agents propose, a person publishes
Agents write through the site's own MCP server with a separate token. Their edits to a live page go into a review queue, and the page stays unchanged until an editor publishes. Details are in the article on draft permissions.
Facts apart from prose
Opening hours, prices and phone numbers are stored as separate facts with a source and check date. One fact can be checked without rereading the whole page, and "open now" comes from schedules, not from text.
Cookieless first-party analytics
The script is under 2 KB, IPs are not stored, and visitors are identified by a hash that changes daily. The reasons: Russian personal data law (152-FZ) and keeping traffic away from outside services.
Stack
- Nuxt 4
- Vue
- Reka UI
- PostgreSQL
- Drizzle ORM
- MapLibre GL and PMTiles
- sharp
- Zod
- @nuxtjs/mcp-toolkit
- Docker on Dokploy
Status and next
The site is live. Partner offers already show on pages, but there are no codes, bookings or payments. Next: move pages to read from the fact layer and test whether the site can earn money.