A subscription SaaS that gives small rental-car operators one place to track every vehicle's condition, cost, and paperwork — built solo, end to end, with Claude Code.
Small rental fleets run on spreadsheets, text threads, and a shoebox of paper mechanic receipts. Tag renewals slip. Insurance lapses go unnoticed until a claim. And there's rarely any record of what a car actually looked like before it left the lot versus when it came back.
Fleet Priority replaces that with a single dashboard per operator: every vehicle's tag, insurance, mileage, payoff status, maintenance history, and condition in one place, with real accounts, real subscriptions, and real accountability — not a shared spreadsheet anyone can silently edit.
It ships as a two-tier subscription product (Basic and Pro), with Stripe handling billing and a feature gate separating the tiers, so it's a real business, not just an internal tool.
Every vehicle as a card: status, tag expiration, tires, mechanic, and a payoff bar that decays automatically each month from a monthly-payment figure, so balances stay current without manual updates. Search by tag, VIN, make, model, or mechanic; filter by status; sort by mileage, year, or tag.
Maintenance history with attached receipts, a per-vehicle gas-cost trend chart plotting every individual fill-up on a fixed axis, insurance documents and policy tracking (Pro), and a preferred-mechanic contact — all locked to view-only until an explicit Edit is pressed, so nothing changes by accident.
A fixed six-point photo checklist — front, rear, each side, interior, odometer — captured straight from a phone camera. The distinguishing move: starting a new inspection automatically pulls up the same vehicle's last inspection photos side by side, so damage gets judged against the last known state, not memory. Each finding carries a MINOR or MAJOR severity tag and a note.
Spend broken down by service type, month-over-month oil-change and gas-cost trends, and a running log of recent maintenance across the whole fleet — the numbers an owner actually checks before deciding whether a car is worth keeping.
Tag, insurance, and maintenance deadlines surface automatically — overdue items flagged in red, due-soon in amber — with optional email reminders sent on a schedule. Settings covers profile, a theme picker that can follow the OS live, password changes, and a list of every signed-in device with per-device sign-out.
The interesting parts weren't the CRUD screens. A few real problems came up along the way — here's how each got run down.
Deleting a vehicle sometimes left its maintenance records behind. The cause: the data layer read the JSON file fresh, mutated it, and wrote it back — twice, in two separate calls — so the second write could clobber the first before it landed. The fix wasn't a patch on the delete route; it was restructuring the whole store around one shared in-memory copy with serialized writes, so every mutation is immediately visible to the next one regardless of disk timing.
Auth started as a bare JWT — fine for "is this user logged in," useless for "sign this one device out." Reworked so every login mints a server-tracked session record and the token carries a session id instead of just a user id. That's what makes per-device revocation possible, and what lets a password change safely kill every other session in one move without guessing which token belongs to which browser.
Checkout worked in testing, then failed in production with Managed Payments is not supported on API version 2024‑06‑20. The account had a newer Stripe feature enabled than the SDK's default API version supported. Fix was to stop relying on the SDK's default and pin the API version explicitly — the kind of bug that only shows up against a real account, not a sandbox.
Deployed to a plain Ubuntu VM rather than a managed platform, since the JSON-file store and uploaded photos need a persistent disk: Node process managed by pm2, nginx as reverse proxy, DNS delegated through Route 53, TLS via Let's Encrypt, and a live Stripe webhook endpoint wired up for real subscription events.
| Backend | Node.js & Express, REST API under /api/* |
| Data | JSON-file store, in-memory cache with serialized writes — documented seam to swap in Postgres at scale |
| Auth | JWT in an httpOnly cookie, bcrypt password hashing, server-tracked sessions for device management |
| Payments | Stripe Checkout, subscriptions, webhooks, promotion codes |
| Frontend | Vanilla JS, HTML, CSS — no framework — Chart.js for trend charts |
| Resend API for password resets & reminders, console-log fallback for local dev | |
| Infra | AWS Lightsail (Ubuntu), nginx, pm2, Let's Encrypt, DNS on Route 53 |