We built DEV3 AI Restaurant Menu & Online Ordering as a WordPress plugin in PHP with a React admin, a mobile-first ordering front end and a standalone kitchen board. Menus, sections, items, modifier groups, tables, orders and imports live in their own tables.
Key design decisions
- One quote function decides the price. The browser sends item IDs, quantities and option IDs only.
Pricing::quote() checks that each item exists, isn't sold out and is available at the order time (menu and section windows), enforces each modifier group's minimum and maximum, caps quantities at 50, then adds the delivery fee for the matched postcode zone, the free-delivery threshold, the minimum order and the tip.
- Postcode zones without a map API. Zones match exact postcodes, prefixes like
SW1*, numeric ranges like 1000-1099 or a catch-all *, in order, so a central zone can sit in front of an outer one.
- One hidden WooCommerce product per order, not per dish. Online payment adds a single virtual "Food order" line priced at the server subtotal, with delivery and tip as cart fees and the quantity locked. Payment, on-hold, failure, cancellation and refund are mapped back onto the restaurant order, through HPOS-safe order APIs.
- The kitchen only sees payable orders. Pay-at-counter orders go straight to the board; online orders wait as
pending_payment and expire after 60 minutes if unpaid. A named lock re-checks slot capacity so two guests can't take the last place in a time slot.
- A board built for a kitchen. New, Preparing and Ready columns, elapsed timers that turn amber at 10 minutes and red at 20, a WebAudio chime, full-screen and dark modes, refresh every 10 seconds, and a Kitchen staff role that can open the board and nothing else.
- AI that drafts, never publishes. Menu import from up to 5 photos or a PDF produces a reviewed draft with warnings for missing prices and dishes already on a menu. Descriptions, pairings and cart suggestions are drafts or offers only, and cart suggestions fall back to rules when AI is off.
Architecture
The menu is server-rendered HTML with Menu JSON-LD, sticky section chips, dietary filters and the 14 EU allergens. Ordering opens in sheets for item options, the order drawer and a one-page checkout for pickup, delivery or dine-in, with ASAP or a time slot computed from opening hours, closed dates, lead time and capacity. Table QR codes carry a rotating token, so reprinting invalidates old cards. Customers follow their order on a status page that refreshes every 15 seconds. The API client, settings, jobs and usage logs come from a shared core used across DEV3's plugins.