Files
carmanagement/docs/project-design/FEATURES.md
T
2026-05-06 22:58:23 -04:00

311 lines
16 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# Features & Priorities — RentalDriveGo
## MVP (Phase 1) — Must Ship Before Launch
### Subscription & Billing
- [x] Company signup → plan selection → payment via AmanPay or PayPal
- [x] 14-day free trial (no payment required until trial ends)
- [x] Company status: PENDING → TRIALING → ACTIVE / PAST_DUE / SUSPENDED
- [x] Subscription gate middleware on all dashboard API routes
- [x] Trial / past-due banners in dashboard
- [x] Suspended account blocks dashboard; public site stays up
- [x] Manual renewal flow: company pays via AmanPay (card/cash/e-wallet) or PayPal
- [x] Invoice history (AmanPay transaction IDs or PayPal capture IDs)
- [x] Supported currencies: MAD, USD, EUR
### Tenant Isolation (Fleet Management)
- [x] Every Prisma query scoped by `companyId`
- [x] `requireTenant` middleware attaches `companyId` from authenticated employee
- [x] Vehicle, customer, reservation IDs validated against `companyId` before any operation
- [x] No cross-company data exposure — enforced at API level, not just UI
- [x] Add / edit / archive vehicles
- [x] Vehicle photos (Cloudinary)
- [x] Published / unpublished toggle (controls marketplace + public site visibility)
- [x] Vehicle categories, specs, features list
### Offers / Promotions System
- [x] Create offer (%, fixed amount, free day, special rate)
- [x] Valid from / until dates
- [x] Applicable to: all vehicles / by category / specific vehicles
- [x] Optional promo code + max redemptions
- [x] Minimum rental days
- [x] `isPublic` flag — show on global marketplace
- [x] `isFeatured` flag — featured carousel placement (plan-gated: GROWTH+)
- [x] Offer applied at booking (discount calculated, stored on Reservation)
- [x] Offer performance stats (redemptions, revenue impact)
- [x] Offer banner image upload
### Global Marketplace (RentalDriveGo.com/explore)
- [x] Featured offers carousel on /explore home
- [x] Search vehicles by city, dates, category, price range
- [x] Company cards (logo, rating, offer badge)
- [x] Company marketplace profile page (vehicles + offers + reviews)
- [x] Vehicle detail page (photos, specs, redirect CTA to company site)
- [x] Cross-company availability check
- [x] Filter by category, transmission, price, features
- [x] Marketplace listing toggle per company (opt out)
### Renter Account System
- [x] Renter signup / login (own auth, separate from Employee/Clerk)
- [x] Email verification
- [x] Renter profile (name, phone, locale, currency)
- [x] Cross-company reservation history in /renter/dashboard
- [x] Save / unsave companies
- [x] Guest booking (no account required, but prompted to sign up after)
- [x] When renter books, auto-create Customer record in that company's CRM
### Online Reservations (all sources)
- [x] Booking from dashboard (employee creates manually)
- [x] Booking from company public site (BookingSource: PUBLIC_SITE)
- [x] Booking from global marketplace (BookingSource: MARKETPLACE)
- [x] Reservation lifecycle: DRAFT → CONFIRMED → ACTIVE → COMPLETED
- [x] Offer / promo code applied at booking step
- [x] Availability check before confirming
- [x] Booking confirmation (number, summary, company contact)
- [x] Cancel with reason + `cancelledBy` (COMPANY / RENTER / SYSTEM)
### Branding & White-Label Public Site
- [x] Company display name, logo, tagline, hero image
- [x] Primary brand color picker
- [x] Subdomain: `{slug}.RentalDriveGo.com` (claimed during onboarding)
- [x] Real-time subdomain availability check
- [x] Vercel wildcard domain routing (`*.RentalDriveGo.com`)
- [x] Company public site: home with offers, vehicle listing, vehicle detail, booking, confirmation
- [x] Offers page on public site
- [x] "Powered by RentalDriveGo" badge (removable on Pro)
- [x] Site language + currency preference
### Payments — Rental (AmanPay + PayPal)
- [x] Company connects their own AmanPay merchant account (Merchant ID + Secret Key)
- [x] Company connects their own PayPal business account
- [x] Collect payment at booking (marketplace redirect + public site)
- [x] AmanPay widget: national card, international card, cash (3000+ points), e-wallet
- [x] PayPal buttons component (standard checkout)
- [x] If no payment method configured: "Contact to reserve" + pay on pickup flow
- [x] Payment status per reservation
- [x] Refund on cancellation (via AmanPay or PayPal API)
- [x] Guest checkout (no renter account required)
### Notifications — Full System
- [x] **Email** (Resend) — all notification types, rich HTML templates
- [x] **SMS** (Twilio) — confirmations, reminders, payment alerts
- [x] **WhatsApp** (Twilio WhatsApp API) — confirmations, reminders (key for AR/FR)
- [x] **In-App** (Socket.io + Redis) — real-time bell icon in dashboard + renter site
- [x] **Push** (Firebase FCM) — renter PWA push notifications
- [x] `Notification` table — logs every delivery attempt per channel
- [x] `NotificationPreference` table — per-user opt-in/out per type + channel
- [x] Preferences UI: matrix toggle (notification type × channel)
- [x] All company events: new booking, cancelled, payment received, trial ending, maintenance due, offer expiring, new review
- [x] All renter events: confirmed, 24h reminder, 2h reminder, vehicle ready, return reminder, cancelled, refund, new offer from saved company, review request
- [x] Scheduled notifications via cron (reminders, trial ending, maintenance due)
### Reviews
- [x] Renter submits review (only after reservation COMPLETED)
- [x] 15 stars overall + vehicle + service
- [x] Text comment
- [x] Company can reply to review
- [x] Reviews shown on marketplace company profile
- [x] Average rating on company card + brand settings
### Customer CRM
- [x] Auto-created from any booking source
- [x] Company-scoped view (never cross-company)
- [x] Linked to global Renter account (if booked as logged-in renter)
- [x] Rental history, notes, flag/blacklist
### Auth & Onboarding
- [x] Company employee auth via Clerk
- [x] Renter auth via own JWT (separate)
- [x] Onboarding step 2: branding + subdomain
- [x] Onboarding step 4: "Your vehicles now appear on the RentalDriveGo marketplace"
- [x] Role system: OWNER / MANAGER / AGENT
### Platform Admin Panel
- [x] `AdminUser` model: email, password (bcrypt), role (SUPER_ADMIN/ADMIN/SUPPORT/FINANCE/VIEWER), 2FA (TOTP), last login tracking
- [x] `AdminPermission` model: per-admin resource+action overrides on top of role defaults
- [x] `AuditLog` model: every admin action logged (action, resource, before/after JSON, IP, note)
- [x] Admin JWT auth (separate from Clerk and renter JWT) — 8h expiry
- [x] TOTP 2FA: setup with QR code, verify, enforce for ADMIN+ roles
- [x] Role hierarchy: VIEWER < FINANCE < SUPPORT < ADMIN < SUPER_ADMIN
- [x] Admin role access matrix: 17 dashboard features × 5 roles
- [x] `admin.RentalDriveGo.com` separate app (Next.js)
- [x] **Company management**: list, search/filter, create, edit, suspend, reactivate, delete
- [x] **Company staff management**: list employees per company, add employee, edit (name/email/role), deactivate/reactivate, reset password
- [x] **Impersonation**: ADMIN+ can log in as any company employee (Clerk impersonation session), with dashboard banner
- [x] **Subscription override**: force status, change plan, add free period with auto-revert
- [x] Manual invoice mark-as-paid
- [x] **Renter management**: list, search, view history, block/unblock
- [x] **Audit log UI**: searchable, filterable by admin/action/company, CSV export
- [x] Admin user management (SUPER_ADMIN only): create/edit/deactivate admins, set roles
- [x] Platform metrics: MRR, churn, active companies, marketplace stats, notification delivery rates
- [x] Prisma seed creates first SUPER_ADMIN from env vars
- [x] Employee role control matrix (OWNER/MANAGER/AGENT) with 17 feature permissions documented
---
### Advanced Rental Operations (Phase 1)
#### Vehicle Damage Inspection
- [x] Interactive top-down SVG damage map in check-in/check-out workflow
- [x] 22 clickable zones (hood, roof, doors, fenders, bumpers, wheels, windshield, mirrors, interior, undercarriage)
- [x] 5 severity levels per zone: SCRATCH, DENT, CRACK, MISSING, OTHER — each shown in distinct color
- [x] Optional note per damaged zone
- [x] Optional damage photos upload (Cloudinary)
- [x] `DamageReport` model — one per check-in, one per check-out (`@@unique([reservationId, type])`)
- [x] Fuel level and odometer recorded at each inspection
- [x] Customer acknowledgement timestamp + name
- [x] Damage map rendered in PDF contract (static SVG with color markers) — CHECKIN + CHECKOUT side by side
#### Insurance Policies
- [x] `InsurancePolicy` model: name, type (CDW, SCDW, THEFT, THIRD_PARTY, FULL, BASIC, ROADSIDE, PERSONAL, CUSTOM)
- [x] Three charge types: PER_DAY, PER_RENTAL (flat), PERCENTAGE_OF_RENTAL
- [x] Required vs optional flag — required policies auto-apply, cannot be opted out
- [x] `ReservationInsurance` junction: snapshot of policy terms locked at booking time
- [x] `insuranceTotal` cached on Reservation for fast invoice generation
- [x] Insurance line items in customer invoice with charge type label
- [x] Insurance shown on rental contract
#### Second / Additional Driver
- [x] `AdditionalDriver` model: full personal details + license info
- [x] Charge types: FREE, PER_DAY, FLAT
- [x] Company configures default charge in `ContractSettings`
- [x] License validation applied to additional drivers (same 3-month rule)
- [x] Additional driver(s) listed on contract + invoice line item (if charged)
- [x] Employee can approve/deny flagged additional driver license
#### Driver License Validation
- [x] `licenseExpiry`, `licenseIssuedAt`, `licenseCountry`, `licenseNumber`, `licenseCategory` fields on Customer
- [x] `LicenseStatus` enum: PENDING, VALID, EXPIRING, APPROVED, DENIED, EXPIRED
- [x] **3-month rule**: if license expires within 90 days → status=EXPIRING → requires employee approval
- [x] **Expired**: status=EXPIRED → automatic flag → employee must explicitly approve or deny before confirmation
- [x] License validation badge on customer record (green/amber/red)
- [x] Warning banner on reservation detail when customer has EXPIRING or EXPIRED license
- [x] Approve / Deny buttons for OWNER and MANAGER roles only
- [x] Approval logged: who approved, when, and note
#### Age-Based & Experience-Based Pricing Rules
- [x] `PricingRule` model: configurable per company
- [x] Conditions: AGE_LESS_THAN, AGE_GREATER_THAN, LICENSE_YEARS_LESS_THAN, LICENSE_YEARS_GREATER_THAN
- [x] **Default rule: Under-25 surcharge** (+15% of base rental, configurable)
- [x] **Default rule: 5+ years experience discount** (5%, configurable)
- [x] Adjustment types: PERCENTAGE, FLAT_PER_DAY, FLAT_TOTAL
- [x] Rules applied to primary driver AND all additional drivers (each rule applied once even if multiple drivers qualify)
- [x] Rules shown as line items on invoice (surcharges positive, discounts negative)
- [x] Snapshot of applied rules stored in `Reservation.pricingRulesApplied` JSON
#### Fuel / Gasoline Policy (Structured)
- [x] `FuelPolicyType` enum: FULL_TO_FULL, FULL_TO_EMPTY, SAME_TO_SAME, PREPAID, FREE
- [x] Multilingual policy description auto-generated from type (EN/FR/AR)
- [x] Optional custom note added by company
- [x] Fuel level recorded at check-in AND check-out via `DamageReport.fuelLevel`
- [x] Policy printed on contract in customer's language
#### Full Invoice Price Breakdown
- [x] Line items: base rental × days, per insurance policy, additional driver (if charged), pricing rule surcharges, pricing rule discounts, security deposit (refundable label)
- [x] Category labels per line: RENTAL, INSURANCE, ADDITIONAL_DRIVER, SURCHARGE, DISCOUNT, DEPOSIT
- [x] Tax/VAT line (if `ContractSettings.showTax = true`)
- [x] Subtotal → discounts → surcharges → insurance → tax → deposit → GRAND TOTAL
- [x] All amounts formatted in company's currency and locale
#### Billing Period Reporting (Accountant Export)
- [x] Reports page at `/dashboard/reports`
- [x] Preset periods: This Week, This Month, This Year, Custom range
- [x] Summary cards: total bookings, base revenue, discounts given, insurance collected, additional driver revenue, net collected
- [x] Full reservations table: contract#, invoice#, customer, vehicle, plate, dates, days, base, discount, insurance, additional driver, pricing adjustments, total, payment status, source
- [x] Export as CSV (one click) — for import into accounting software (QuickBooks, Sage, etc.)
- [x] Report generated on-demand from DB — no pre-computed tables
---
## Phase 2 — Post-Launch
### Fleet Enhancements
- [ ] Maintenance log with cost tracking
- [ ] Maintenance due alerts (date + mileage)
- [ ] Vehicle availability calendar view in dashboard
### CRM Enhancements
- [ ] Repeat customer detection + discount
- [ ] Customer communication log (emails sent)
- [ ] Customer lifetime value stat
### Analytics
- [ ] Revenue chart (day/week/month)
- [ ] Fleet utilization rate + underperforming vehicles alert
- [ ] Offer ROI analysis (revenue gained vs discounted)
- [ ] Marketplace impressions per vehicle
- [ ] CSV export
### Renter Experience
- [ ] Renter "Continue with Google" auth
- [ ] Favorite vehicles across companies
- [ ] Renter profile completion % indicator
- [ ] Booking modification request (change dates)
### Public Site Enhancements
- [ ] About page with company description + team photo
- [ ] Google Maps embed for pickup location
- [ ] "Request to book" mode (no immediate payment)
- [ ] WhatsApp floating button
---
## Phase 3 — Growth
### Custom Domain (Pro)
- [ ] Company enters `cars.acme.com` in /dashboard/brand
- [ ] Vercel API auto-provisions domain
- [ ] DNS instructions shown
- [ ] SSL automatic
### Marketplace Enhancements
- [ ] City/region pages (`/explore/cities/paris`)
- [ ] Renter 2FA
- [ ] Sponsored listing (pay-per-click for marketplace placement)
- [ ] AI-powered vehicle recommendations based on renter history
### Advanced Offers
- [ ] Flash sales (limited time countdown timer)
- [ ] Loyalty program (repeat renter discounts)
- [ ] Bundle offers (car + extras)
### Integrations
- [ ] Google Calendar sync
- [ ] QuickBooks export
- [ ] Zapier webhooks
### Documents — Rental Contracts & Customer Bills
- [x] `ContractSettings` model: per-company legal name, RC/ICE number, tax ID, custom terms, fuel/deposit/damage policies, additional clauses, signature block, footer notes, invoice tax settings, numbering prefixes
- [x] `contractNumber` + `invoiceNumber` fields on Reservation — assigned once via atomic DB transaction, never reset
- [x] `checkInFuelLevel` / `checkOutFuelLevel` fields for contract accuracy
- [x] **Rental Contract PDF** — branded with company logo + name + primary color, contains: customer details, vehicle data + cover photo, rental dates/locations, financial table (rate × days discount + deposit), all policy clauses, full T&Cs, signature lines (company + customer)
- [x] **Customer Invoice PDF** — branded, contains: company legal info + tax ID, bill-to block, line items table (vehicle, deposit, tax if configured), totals (subtotal, discount, tax, grand total), payment details (AmanPay/PayPal transaction ID, paid date), PAID/PENDING stamp
- [x] **Both documents support EN / FR / AR** — all labels, date formats, and currency format per company locale
- [x] **On-demand generation** — PDFs are NEVER stored. Generated fresh from DB data on every request. No Cloudinary PDF upload.
- [x] **Streaming PDF response**`Content-Type: application/pdf`, `Content-Disposition: inline` (view in browser tab) or `attachment` (download)
- [x] **Print from browser** — user opens PDF in new tab and prints via native browser print dialog
- [x] **Email with PDF attachment** — Resend sends email with both documents as attached PDFs
- [x] **Send contract + invoice together** — single API call generates both and attaches both to one email
- [x] **Custom recipient email** — override the customer's email address when sending (for forwarding)
- [x] **Renter self-download** — renter can download their own contract/invoice from `/renter/dashboard`
- [x] **Settings preview** — preview contract/invoice PDF with real company branding + sample data before finalizing settings
- [x] **Automatic triggers**: invoice sent on payment confirmed; contract sent on check-in completed
### Multi-location per company
- [ ] Multiple pickup/return locations
- [ ] Location-aware vehicle assignment
- [ ] Distance filter on marketplace
---
## Out of Scope
- GPS / telematics
- Driver license OCR / ID verification
- Insurance products
- Fuel management
- Peer-to-peer (this is B2B SaaS + B2C marketplace, not P2P)
- Native mobile app (PWA covers push notifications)