My finance app FinMan VHWorx reads utility meters, fuel receipts and bank statements from photos and files. All of it runs on vision/text LLMs via OpenRouter — and a lot of it on free-tier models.
Free models are great except for one thing: they churn constantly. They appear, disappear, get renamed or silently deprecated. Hardcode a model id, and your feature dies quietly on a random Tuesday.
So FinMan stopped treating models as constants. Models are data:
- A daily job syncs the live model list from OpenRouter. New free vision models are added automatically; vanished ones are deactivated.
- Paid fallbacks re-rank by price daily. The Gemini Flash family backs up the free tier, cheapest first — so a failover never surprises the bill.
- Recognition walks the priority list. If a model errors or is gone, the next one takes over. One dead model never breaks a user's photo.
- The app upgrades itself. A separate job pins the top model from a public community leaderboard as priority #1 — so text tasks quietly move to whatever is currently best.
- Changes ping me on Telegram. No dashboards to check.
The result after months in production: I haven't touched a model id since. Every deprecation wave passed unnoticed — by me and by users.
If you're building on LLMs (especially free tiers), this is the highest-leverage small change I know: models as data, not constants. A table, a daily cron, a priority walk. That's the whole trick.