Appearance
Scheduled Orders
Overview
Scheduled orders allow customers to place orders for future pickup or delivery times instead of ASAP.
Key Purpose: Enable advance ordering for future times.
Purpose
This feature lets customers place online orders for future pickup or delivery times by selecting from available time slots calculated from business hours and order capacity.
Key Concepts
- Time Slots: Generated from business hours (or custom availability schedule) at intervals set by
time_slot_duration_min(default 30 minutes), filtered by order capacity limits - Per-Channel Scheduling: Each channel (pickup/delivery) has independent enable/disable toggles and days-in-advance limits (max 365 days)
- Capacity Checking: Available timeslots are validated against order capacity using database locking with retries (up to 3 attempts, 200ms between) to prevent double-booking
- Send to POS Timing: The
send_to_possetting controls whether scheduled orders appear on KDS immediately upon placement or are held until the scheduled pickup/delivery time - Custom Scheduled Orders: Advanced mode with
hours_in_advanceandminutes_before_pickup_delivery_timethresholds for fine-grained control of when orders are sent to KDS
Actions
Enable Scheduled Pickup Orders
Toggle schedule_order_for_future_days.takeout.enabled and set days_in_advance (1-365) to allow customers to schedule pickup orders.
Enable Scheduled Delivery Orders
Toggle schedule_order_for_future_days.delivery.enabled and set days_in_advance (1-365) independently from pickup scheduling.
Configure Accept Orders Until
Choose "Closing Time" or "Closing Time Minus Prep Time" to control when the last time slot is available before the restaurant closes.
Enable Custom Availability
Toggle custom availability to define specific hours when scheduled orders are accepted, overriding the default business hours.
Configure Send to POS Behavior
Set send_to_pos to "pickup_delivery_time" (hold until scheduled time) or "order_placed" (send immediately). For custom scheduled orders, set hours_in_advance and minutes_before_pickup_delivery_time thresholds.
Location
- Backoffice Route:
/pickup-and-delivery/online-ordering - Vue Component:
src/views/pickup-and-delivery/online-ordering/forms/FullfilmentAndScheduling.vue
Fields
Takeout Scheduling
| Property | Value |
|---|---|
| Field ID | schedule_order_for_future_days.takeout.enabled |
| Label | Allow Scheduled Pickup |
| Type | Toggle |
| Default | true |
Description: Allow customers to schedule pickup orders.
Takeout Days in Advance
| Property | Value |
|---|---|
| Field ID | schedule_order_for_future_days.takeout.days_in_advance |
| Label | Days in Advance |
| Type | Number |
| Default | 30 |
| Min | 0 |
| Max | 365 |
Description: How many days ahead customers can schedule.
Delivery Scheduling
| Property | Value |
|---|---|
| Field ID | schedule_order_for_future_days.delivery.enabled |
| Label | Allow Scheduled Delivery |
| Type | Toggle |
| Default | false |
Description: Allow customers to schedule delivery orders.
Delivery Days in Advance
| Property | Value |
|---|---|
| Field ID | schedule_order_for_future_days.delivery.days_in_advance |
| Label | Days in Advance |
| Type | Number |
| Default | 30 |
| Min | 0 |
| Max | 365 |
Description: How many days ahead customers can schedule delivery.
Time Slot Generation
Accept Orders Until
| Property | Value |
|---|---|
| Field ID | accept_orders_until |
| Label | Accept Orders Until |
| Type | Select |
| Options | Closing Time, Closing Time Minus Prep Time |
| Default | Closing Time |
Description: When to stop accepting orders.
Options:
- Closing Time: Accept orders until closing
- Closing Time Minus Prep Time: Stop accepting before closing to allow prep
Custom Availability
| Property | Value |
|---|---|
| Field ID | custom_availability |
| Label | Custom Availability |
| Type | Toggle |
| Default | false |
Description: Use custom schedule instead of business hours.
Business Logic
Time Slot Generation
Customer selects date
│
▼
Get business hours for that day
│
▼
Custom availability enabled?
├── Yes → Use custom schedule
└── No → Use business hours
│
▼
Generate time slots based on:
- Time slot duration (from order capacity)
- Available capacity per slot
- Accept orders until setting
│
▼
Filter out:
- Past time slots (for today)
- Fully booked slots
- Restricted dates
│
▼
Return available time slotsOrder Processing
Scheduled order placed
│
▼
Store with scheduled time
│
▼
Send to POS setting?
├── Pickup/Delivery Time → Hold until scheduled time
└── Immediately → Send now, mark as scheduled
│
▼
KDS shows order at appropriate timeBusiness Rules
- Past time slots are filtered out for today's date; fully booked slots are excluded based on order capacity limits
- Days with no business hours or marked as restricted dates are unavailable for selection in the customer-facing date picker
- The system uses database locking with retries to prevent double-booking of capacity slots during concurrent order submissions
- Kiosk and dine-in (ForHere) orders bypass the time slot capacity system entirely and always use the current time
- Prep time is calculated as: location average prep time + channel delay (delivery or pickup) + maximum individual item prep time, capped at 24 hours (1440 minutes)
FAQs
- "Can scheduled orders be enabled for delivery but not pickup?" Yes, each channel has independent
enabledanddays_in_advancesettings. You can enable one without the other. - "What happens if a time slot fills up while a customer is selecting it?" The backend checks capacity at order submission time using database locks. If the slot is full, the system attempts to find the next available slot or split across adjacent slots.
- "How often are available time slots refreshed?" The available timeslots endpoint caches results for 60 seconds. Cache is cleared when a new transaction is processed for that location.
- "What does 'Closing Time Minus Prep Time' mean?" It stops accepting orders earlier than closing time to ensure the kitchen has enough prep time before close. The last slot is offset by the average prep time.
- "When does a scheduled order appear on the KDS?" Depends on
send_to_pos: with "pickup_delivery_time" it appears near the scheduled time; with "order_placed" it appears immediately. Custom scheduled orders add further control viahours_in_advancethresholds.
Troubleshooting
- No time slots available for a day → Check that the location has business hours configured for that day and that the day is not marked as a restricted date. Also verify order capacity limits are not set to zero.
- Scheduled order not appearing on KDS → Check the
send_to_possetting. If set to "pickup_delivery_time," the order is held until near the scheduled time. If set to "order_placed," it should appear immediately. - Customer seeing "slot full" error → The time slot has reached its order capacity limit. Increase the limit in Order Capacity settings, or the customer can try a different time slot.
- Days in advance not working → Verify
schedule_order_for_future_daysis enabled for the correct channel (takeout or delivery) and thatdays_in_advanceis set to a value greater than 0.
Customer Impact
Online Ordering
- Date picker for future dates
- Time slot selection
- Shows available slots only
- Confirmation shows scheduled time
Kiosk
- Option for ASAP or scheduled
- Date/time selection
- Slot availability shown
Time Slot UI
╔═══════════════════════════════════════╗
║ When would you like your order? ║
╠═══════════════════════════════════════╣
║ ║
║ 📅 Today, Dec 5 ║
║ ║
║ ┌─────────┐ ┌─────────┐ ┌─────────┐ ║
║ │ 12:00 │ │ 12:15 │ │ 12:30 │ ║
║ └─────────┘ └─────────┘ └─────────┘ ║
║ ┌─────────┐ ┌─────────┐ ┌─────────┐ ║
║ │ 12:45 │ │ 13:00 │ │ 13:15 │ ║
║ └─────────┘ └─────────┘ └─────────┘ ║
║ ║
║ 📅 Tomorrow, Dec 6 ║
║ 📅 Saturday, Dec 7 ║
║ 📅 Sunday, Dec 8 ║
║ ║
╚═══════════════════════════════════════╝Relations
Depends On
- Business Hours: Available times
- Order Capacity: Slot duration and limits
- Restricted Dates: Blocked dates
Affects
- Transactions: Scheduled time stored
- KDS: Order timing
- Reports: Scheduled vs ASAP orders
Related Features
Examples
Pickup Scheduling Enabled
json
{
"schedule_order_for_future_days": {
"takeout": {
"enabled": true,
"days_in_advance": 30
},
"delivery": {
"enabled": false,
"days_in_advance": 30
}
}
}Both Enabled
json
{
"schedule_order_for_future_days": {
"takeout": {
"enabled": true,
"days_in_advance": 7
},
"delivery": {
"enabled": true,
"days_in_advance": 3
}
}
}Available Time Slots Response
json
{
"date": "2024-12-05",
"time_slots": [
{ "time": "12:00", "available": true, "capacity": 3 },
{ "time": "12:15", "available": true, "capacity": 2 },
{ "time": "12:30", "available": false, "capacity": 0 },
{ "time": "12:45", "available": true, "capacity": 3 }
]
}Scheduled Order
json
{
"order": {
"id": "order-123",
"dining_option": "Pickup",
"is_asap": false,
"order_date": "2024-12-06 14:30",
"items": [...],
"status": "scheduled"
}
}