From 528fd5e230f90a1c61d481d227f88e65b8e8d490 Mon Sep 17 00:00:00 2001 From: Sean Dean <254259913+distronode-com@users.noreply.github.com> Date: Fri, 4 Sep 2026 04:36:35 -0400 Subject: [PATCH] =?UTF-8?q?docs:=20CLAUDE.md=20=E2=80=94=20the=20embed=20w?= =?UTF-8?q?idget=20does=20not=20load=20booking-logic.js?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The booking-calendar section told an agent that shared slot logic "lives in internal/handler/assets/booking-logic.js ... not per-surface", listing the embed widget as one of the three surfaces. Following that instruction and calling BookingLogic from embed.js ships a ReferenceError to the customer's site, where no test in this repo would see it. We came close to doing exactly that. Checked rather than assumed: - embed_handler.go embeds embed.js with //go:embed and serves the bytes unmodified (http.ServeContent over bytes.NewReader(embedJS)). Nothing prepends the module. - bookingLogicJS is referenced only by book.go and manage_handler.go, which inline it into their templates. - embed.js's own comment at line 42 already says the widget "doesn't import that module", and it carries local dowLabels, dayKey, timeLabel, shortDay and ymd for that reason. So the entry now says which two surfaces load the module, states plainly that BookingLogic is undefined in the widget and why (standalone file, Shadow-DOM component on a third-party page, no build step), and gives the rule: put shared page logic in booking-logic.js, and mirror it into the widget deliberately when the widget needs it too. CLAUDE.md only. docs/ARCHITECTURE.md §8 and the module's own header make the same claim and are corrected in the branch behind PR #23, so this one stays out of their way. --- CLAUDE.md | 13 +++++++++++-- 1 file changed, 11 insertions(+), 2 deletions(-) diff --git a/CLAUDE.md b/CLAUDE.md index 0037a37..91ab512 100644 --- a/CLAUDE.md +++ b/CLAUDE.md @@ -51,8 +51,17 @@ behaviour or markup must usually be made in all three, or they drift: implemented separately in each. If you change calendar *behaviour*, update all three. - Verify on **desktop and mobile** for each surface after touching the calendar. - **Shared slot logic lives in `internal/handler/assets/booking-logic.js`** (tested with - `node --test`), not per-surface: day grouping, time formatting, and the taken-slot - merge. Put anything all three need there rather than writing it three times. + `node --test`): day grouping, time formatting, and the taken-slot merge. It is inlined + into **book.html and manage.html only**, which are the two surfaces that load it. +- ⛔ **The embed widget does NOT load `booking-logic.js`, so `BookingLogic` is undefined + inside it.** `EmbedJS` serves `embed.js` as its own standalone file, unmodified — it is a + Shadow-DOM web component on a third-party page, with no build step and nothing to + prepend the module for it. It therefore carries its own copies of the few helpers it + needs (`dowLabels`, `dayKey`, `timeLabel`, `shortDay`, `ymd`), each commented as + mirroring the shared one. Calling `BookingLogic.anything` from `embed.js` throws a + `ReferenceError` on the customer's site, where no test here would see it. So: put logic + the pages share in `booking-logic.js`, and when the widget needs it too, mirror it there + deliberately and keep the two in step. - **Taken/booked slots** (`show_taken_slots`, off by default) are computed by `slots.GenerateWithTaken` as the *difference* between a normal pass and one ignoring busy, which is what keeps out-of-hours and min-notice starts from being mislabelled as