Developer Notes & Integration Guide
Developer Notes & Integration Guide
Overview: Stolik Menu and Stolik Menu PRO expose several public-facing workflows that may be used alongside custom themes, caching layers, multilingual plugins, payment integrations, and other WordPress extensions. This guide details the architectural contracts and state rules developers should preserve when extending or integrating with Stolik.
Public Context Model
Stolik uses a multidimensional context model to determine what kind of menu experience a guest is experiencing. These dimensions describe distinct operational aspects and must not be collapsed into a single value:
Business domain: restaurant | hotelEntity: none | table | locationService mode: base | universal | dedicatedContent channel: food | hotel_servicesDimension Definitions
- Business Domain (
restaurant|hotel): Identifies the overarching operational venue context. - Entity (
none|table|location): Identifies the physical or logical anchor of the session (e.g., Base Menu hasnone, Dedicated Table 5 hastable, and Room 102 haslocation). - Service Mode (
base|universal|dedicated): Describes how the QR/service workflow identifies the guest’s coordinates.
dedicated) participates in different business domains. Never infer the business domain from the service mode alone.Business Domain and Content Channel Are Different Concepts
This is one of the most critical integration rules in Stolik:
- The Business Domain answers: Where is the guest using Stolik?
- The Content Channel answers: What kind of content is being displayed or ordered?
For example, a hotel guest ordering breakfast has domain = hotel and channel = food. A hotel guest requesting extra towels has domain = hotel and channel = hotel_services.
Both requests belong to the Hotel domain, but operate across different content channels. This architecture allows a single Hotel Custom Location to support both In-Room Dining and Hotel Services without fragmenting the guest session.
hotel context = hotel services. Hotel context may contain food-only content, hotel services content, or both depending on the active edition and location setup.Do Not Infer Hotel Context from table_id
Some QR and service flows expose a numeric transport parameter named table_id for legacy backwards-compatibility. Developers must treat this strictly as an opaque transport field.
table_id must not be treated as proof of Restaurant or Hotel identity.
Restaurant Table 2 and Hotel Custom Location #2 may both carry an internal numeric index of 2, but they represent completely different operational entities. The correct mental model is:
// Restaurant Tabledomain = "restaurant"; entity.type = "table";// Hotel Room / Areadomain = "hotel"; entity.type = "location";Opaque Short QR Identities
Stolik Menu PRO 1.6+ uses compact, permanent QR identifiers such as service_qr_id=68d98f3d49. This identifier represents a server-resolved QR identity, eliminating the need to expose long signed tokens in the public browser URL.
Integration Rules for Short QR IDs
- Treat
service_qr_idas an opaque string. - Do not decode it, alter it, or derive semantic meaning from its characters.
- Do not generate IDs manually or assume a fixed character length.
- Never infer table, room, or domain identity by parsing the ID string.
if (serviceQrId.length === 10). Length and format are not part of the public contract and may be adjusted in future releases.Signed Transactional Context
Ordering, payments, service calls, and Charge to Room capabilities are never unlocked simply because a URL contains recognized query parameters like context=hotel or table_id=5.
Transactional capabilities require an authenticated, server-side cryptographic token handshake. This prevents intentional or accidental URL tampering by patrons. Custom integrations must not use raw URL parameters as proof of authorization for privileged service actions.
Fresh QR Scan Precedence
Scanning a physical QR code represents an explicit, authoritative guest action. Therefore:
localStorage, sessionStorage, cookies, or cached runtime data).Scenario:
- Guest scans Hotel Room 102 QR in the morning.
- Guest visits the hotel restaurant in the afternoon and scans Restaurant Table 5.
- Restaurant Table 5 immediately becomes authoritative. Stale hotel state must not leak into the restaurant view.
If developing custom JavaScript wrappers around Stolik, never restore prior location state over a freshly initialized QR payload.
Locale Must Not Change Business Identity
Stolik supports multilingual routing and dynamic locale switching. A language transition affects labels, dish translations, currency formatting, and localized URL paths. It must never alter the guest’s operational identity.
If a guest at Restaurant Table 3 switches from English to Polish, the session must remain Restaurant Table 3 (Polish). It must never mutate into Hotel Location 3 or reveal Hotel Services tabs due to translation fallback logic. Treat locale strictly as a presentation dimension.
Cache Guidance & Rules
Stolik contains both cache-friendly presentation assets and session-sensitive transactional endpoints. Configure your caching layer (Varnish, LiteSpeed, WP Rocket, Cloudflare) according to the table below:
| Resource Type | Examples | Caching Strategy |
|---|---|---|
| Static Assets | CSS, JS, WebP/JPG images, QR previews | Cache Aggressively (Browser & CDN) |
| Base Menus | Static restaurant catalog pages | Standard Page Cache |
| Transactional Endpoints | Virtual Tray, Active Orders, Waiter Calls, Live Dashboard | Bypass Cache Completely |
| Dynamic QR Links | URLs carrying service_qr_id or service parameters | Do Not Cache HTML |
Restaurant and Hotel Context Isolation
Restaurant and Hotel workflows are isolated operational domains. Transitions between them must remain clean:
Restaurant Dedicated Table → Fresh Hotel QR scan → Clean Hotel ContextHotel Custom Location → Fresh Restaurant QR scan → Clean Restaurant Context
Never write integration logic assuming dedicated = restaurant or table_id present = restaurant. Hotel Custom Locations also utilize dedicated-style service flows.
Content Channels & Mixed Orders
Stolik currently manages two primary content channels:
food: Food and beverage items (Restaurant menus, In-Room Dining catalogs).hotel_services: Hospitality workflows (housekeeping, extra amenities, SPA bookings, airport transfers).
In PRO Custom Locations, an active order may contain items from both channels simultaneously (a Mixed Order). Custom integrations and webhook listeners should preserve item-level channel metadata rather than flattening all items into a single generic list.
Charge to Room Is a Capability, Not a Domain Default
Being in a Hotel context does not automatically enable Charge to Room. Charge to Room is a capability gate requiring three distinct preconditions:
Valid Hotel Context + Valid Custom Location + Charge to Room Enabled (Admin) = Capability ActiveA Restaurant context must never gain this capability merely because the PRO plugin is active on the WordPress instance.
QR Identity and Visual Styling
QR identity and QR visual presentation are entirely decoupled. Altering colors, corner rounding, quiet zone margins, or embedded center logos affects only the rendered SVG/PNG canvas. It will never mutate the underlying table ID, room token, or domain binding.
If building custom export pipelines, always consume Stolik’s canonical QR destination string rather than attempting to reconstruct payload URLs from front-end input values.
Public Mode Semantics
| Mode | Domain | Entity Type | Behavioral Contract |
|---|---|---|---|
| Base | restaurant | none | View-only menu. No table binding; ordering actions disabled. |
| Universal | restaurant | table (guest-supplied) | Shared QR. Guest manually selects their table number. |
| Dedicated | restaurant | table (encoded) | Permanent table binding. Table is resolved automatically. |
| Custom Location | hotel | location (encoded) | Permanent room/area binding. Opens hotel channels. |
Stable Interfaces vs Internal Implementation
Stolik evolves rapidly. To maintain long-term upgrade compatibility, developers must distinguish between public extension points and internal implementation details:
Recommended Integration Practices
- Prefer: Standard WordPress action/filter hooks, documented shortcodes, public URL query contracts, and CSS styling hooks.
- Avoid: Reading plugin database options directly via
get_option(), modifying encrypted payload tokens, scraping internal DOM nodes, or overriding internal JavaScript globals.
DOM and CSS Customization
Target documented root classes (such as .stolik-menu-wrapper, .stolik-mobile-mockup) when customizing menu presentation. Avoid selectors that depend strictly on element order (e.g., div > div:nth-child(3)) as DOM layouts adapt between templates.
REST and Transactional Requests
Stolik’s internal REST endpoints require validated session context, nonce verification, and active capability checks. Never attempt to replay captured transactional requests across different tables, rooms, or domains, as server validation will drop the request.
Multilingual Integrations
When using multilingual plugins (e.g., Polylang, WPML), ensure translated menu pages preserve the original query parameters. A redirect that modifies /menu/ to /pl/menu/ must preserve query parameters like service_qr_id to maintain the guest’s table or room authorization.
Testing Recommendations for Integrations
Before deploying custom integrations to production, verify the following workflows in staging:
- Restaurant Base vs Dedicated Table QR scan.
- Hotel Custom Location scan (verify In-Room Dining + Hotel Services tabs).
- Context switching: scan Hotel QR immediately followed by Restaurant QR.
- Locale switching after QR initialization (verify table/room number is retained).
- Placing a new order, appending items, and verifying staff receipt in Live Dashboard.
- Charge to Room flow with feature toggled ON vs OFF.
Compatibility Guidance & Issue Reporting
Always keep Stolik Menu (Free) and Stolik Menu PRO synchronized on identical version releases (e.g., both on v1.6.0).
When submitting a technical integration ticket to support@brightforce.pl, please include:
- Plugin versions (Free & PRO) + WordPress and PHP versions.
- Active caching, CDN, and multilingual plugins.
- Configured QR Mode (Base, Universal, Dedicated, or Custom Location).
- Browser console logs and network response status codes.