Rental customers in Morocco expect to negotiate a booking in a conversation, usually on WhatsApp, rather than fill in a multi-step form. The platform had to accept both.
My role
Sole developer — data model, application, admin API and both automation agents.
How it's built
Next.js with Prisma over a relational schema for the fleet, availability and reservations.
Zod schemas validating input at the API boundary, shared with the automation layer.
A web chat agent that holds conversation state in n8n data tables across turns, completes a reservation, writes it to the application database and notifies admins on WhatsApp.
An admin agent that collects car details conversationally, maps free text onto the Prisma enums, and posts to the admin API — so adding a vehicle is a chat, not a form.
What was actually hard
Conversational booking is stateful across many turns, and a stateless webhook has no memory — state is persisted per conversation so a dropped message does not restart the booking.
Free-text vehicle descriptions have to land exactly on constrained enum values, so the mapping is validated against the schema rather than passed straight through.
Anything an agent writes goes through the same validation as the web forms; the bot is a client of the API, never a shortcut around it.