Ezy Car Rentals started the way most of my products do: a client needed something that didn't exist.
A car rental company in Jamaica was running their entire operation through WhatsApp and a notebook. Literally — hand-written records of which cars were rented, when they were due back, and how much was owed. No website. No booking system. No digital anything.
They wanted a website. What they actually needed was a complete business system.
This is the story of how that client project became a product — and what I learned building it.
The Problem
Car rental is operationally complex. It looks simple from the outside — rent car, return car — but the behind-the-scenes reality is different:
- Fleet visibility: Which cars are available right now? Which are rented? In maintenance?
- Pricing complexity: Daily rates, weekly discounts, monthly specials, security deposits, insurance options
- Availability conflicts: Can't rent the same car to two people at once (you'd be surprised how often this happens with manual tracking)
- Booking management: Customer details, pickup times, return dates, extensions, early returns
- Financial tracking: Deposits collected, refunds due, balances owed
Most car rental software is designed for enterprise operators with hundreds of vehicles. The pricing reflects that — thousands per month, complex integrations, features a small operator will never use.
My client had 12 cars. They needed something simpler.
I'm not looking for Hertz software. I just want to know which cars are out, who has them, and when they're coming back. And maybe stop doing everything on WhatsApp.
Version 1: Solving the Immediate Problem
The first version was built specifically for that one client. Basic features:
- Vehicle list with status (available, rented, maintenance)
- Simple booking form capturing customer details
- Calendar view showing which cars were booked when
- Admin dashboard in WordPress
Nothing fancy. Just digitizing what they were doing in the notebook.
v1.0 - The MVP
Basic CRUD for vehicles and bookings. Calendar view. WordPress admin integration. Solved the immediate problem but wasn't a "product" yet.
It worked. Client was happy. But I noticed something: the code I wrote for them would work for any small car rental operation. Same problems, same solutions.
That's when I started thinking about productization.
Building the Product
Turning client code into a product meant making it configurable, maintainable, and robust enough for multiple deployments.
Architecture Decisions
I followed the same patterns as Ezy Travels Pro:
ezy-car-rentals/
├── ezy-car-rentals.php // Main plugin file
├── includes/
│ ├── class-vehicle.php // Vehicle CPT and logic
│ ├── class-booking.php // Booking management
│ ├── class-availability.php // Availability calculator
│ ├── class-pricing.php // Rate calculations
│ └── class-api.php // REST endpoints
├── admin/
│ ├── class-admin.php
│ ├── views/
│ └── assets/
├── public/
│ └── assets/
│ └── ezy-car-core.js // Shared frontend framework
└── templates/
Key architectural choice: the ezy-car-core.js framework. This is shared JavaScript that handles the booking interface on static HTML sites, communicating with WordPress via REST API. Same approach as the tour booking system.
Feature Evolution
Multi-Vehicle Categories
Economy, SUV, Luxury, Bus. Each with different rates and attributes.
Flexible Pricing
Daily, weekly, monthly rates. Free day promotions. Seasonal pricing.
Security Deposits
Per-vehicle deposit amounts. Deposit status tracking. Refund records.
Tax Calculations
Configurable tax rate (16.5% GCT for Jamaica). Automatic calculation on quotes and invoices.
Mobile Admin
PWA-enabled dashboard. Manage bookings from phone. Live polling for new reservations.
Standalone Admin
ezy-admin.php — dedicated admin interface outside WordPress admin. Cleaner UX for operators.
The Hard Problems
Some features sound simple but were surprisingly complex:
Availability Checking
Given a date range, which vehicles are available? Sounds easy until you account for:
- Overlapping bookings (start/end on same day handling)
- Maintenance periods
- Buffer time between rentals (cleaning, inspection)
- Extended rentals that weren't in the system yet
The availability algorithm went through several rewrites before it was bulletproof.
Free Day Promotions
Common promotion: "Rent for 6 days, get 7th day free." Implementing this required:
- Configurable threshold (how many paid days before free kicks in)
- Calculating the discount correctly in quotes
- Displaying it clearly so customers understand the deal
- Making it optional per deployment
Lesson: Promotions Are Complex
Every "simple" promotion has edge cases. What if they extend the rental? What if they return early? What about partial weeks? Build flexibility into the pricing system from the start.
The Mobile Admin Challenge
Car rental operators aren't sitting at desks. They're at the lot, delivering cars to airports, picking up returns. The admin had to work on phones.
WordPress admin on mobile is... not great. So I built ezy-admin.php — a standalone admin interface that loads outside wp-admin. Mobile-first design, touch-friendly controls, PWA support for installation.
Features of the mobile admin:
- Dashboard showing today's pickups and returns
- Quick status updates (mark vehicle as returned)
- Live polling for new booking notifications
- CSV export for accounting
- Offline indicator (knows when connectivity is lost)
Integration Patterns
Static Site + WordPress Backend
Like all Ezy products, this follows the hybrid architecture:
- Public site: Static HTML with JavaScript quote calculator
- Backend: WordPress + Ezy Car Rentals in /wp/
- Communication: REST API for availability, pricing, booking submission
// Frontend: Get availability for date range
const response = await fetch('/wp/wp-json/ezy-cars/v1/availability', {
method: 'POST',
body: JSON.stringify({
start_date: '2026-04-10',
end_date: '2026-04-15',
category: 'suv'
})
});
// Returns: Array of available vehicles with pricing
WhatsApp Integration
Critical for Jamaica. The booking form generates a pre-filled WhatsApp message:
// Generate WhatsApp link
const message = `New booking request:
Vehicle: ${vehicle.name}
Dates: ${startDate} to ${endDate}
Total: $${total} USD
Name: ${customer.name}
Phone: ${customer.phone}`;
const waLink = `https://wa.me/1876XXXXXXX?text=${encodeURIComponent(message)}`;
Customer clicks, WhatsApp opens, message is ready. Operator confirms and processes.
Current State: v7.6
The plugin is now deployed across multiple car rental operations. Current feature set:
🚗 Fleet Management
Unlimited vehicles. Categories. Photos. Specs. Individual pricing. Status tracking.
📅 Availability System
Real-time availability checking. Visual calendar. Conflict prevention.
💰 Flexible Pricing
Daily/weekly/monthly rates. Per-vehicle deposits. Tax calculation. Promotions.
📱 Mobile Admin
PWA dashboard. Live booking notifications. Touch-optimized interface.
💬 WhatsApp Booking
One-click booking via WhatsApp with all details pre-filled.
📊 Reporting
CSV export. Revenue tracking. Utilization metrics.
What I Learned
1. Client Projects Reveal Product Opportunities
The best products solve real problems you've already solved for clients. You know the problem space intimately.
2. Build for Configuration, Not Customization
Every deployment should use the same codebase with different settings. Custom code per client doesn't scale.
3. Mobile-First for Operations
Business owners running physical operations aren't at desks. Build admin interfaces for phones first.
4. Local Context Matters
WhatsApp integration isn't optional in Jamaica. 16.5% GCT calculation must work correctly. JMD + USD support essential. Generic solutions miss these requirements.
5. Iterate Based on Usage
Most features came from operators asking "can it do X?" Real usage reveals what's missing faster than speculation.
What's Next
The roadmap includes:
- Online payments: Deposit collection via Lynk/NCB
- Driver documents: License upload and verification
- Multi-location: Support for operators with multiple lots
- Customer accounts: Return customer recognition and history
- Automated reminders: Return date notifications via SMS/WhatsApp
The product continues to evolve based on what operators actually need.
For Other Developers
If you're thinking about productizing client work:
- Identify the pattern. Did you solve a problem that others have too?
- Abstract the specifics. Turn hardcoded values into configuration.
- Build upgrade paths. Existing clients need to migrate smoothly to product versions.
- Document ruthlessly. You won't remember why you made decisions in 6 months.
- Price for sustainability. Products need ongoing maintenance. Price to fund that.
Ezy Car Rentals exists because I built something once and realized I could sell it multiple times. That's the productization playbook.
Run a Car Rental Business?
Ezy Car Rentals might be exactly what you need. Let's talk about your operation.
Get a Demo