@topy-ai/maggie 0.7.47 → 0.7.48

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (58) hide show
  1. package/README-zh-TW.md +2 -2
  2. package/README.md +49 -15
  3. package/bin/maggie.js +6 -2
  4. package/bundled-contracts/maggie-design/palette-roles-v1.schema.json +47 -0
  5. package/bundled-contracts/maggie-marketplace/template-content-v1.schema.json +103 -0
  6. package/bundled-contracts/maggiedash/booking-browser-evidence-v1.json +21 -0
  7. package/bundled-contracts/maggiedash/booking-browser-evidence-v2.json +191 -0
  8. package/bundled-contracts/maggiedash/booking-email-templates-v1.json +3 -1
  9. package/bundled-contracts/maggiedash/booking-voucher-lifecycle-v1.json +85 -0
  10. package/bundled-contracts/maggiedash/execution-board.json +4629 -1553
  11. package/bundled-contracts/maggiedash/stripe-booking-capabilities-v1.json +1 -0
  12. package/bundled-marketplace/README.md +17 -0
  13. package/bundled-marketplace/catalog.json +56 -7
  14. package/bundled-references/browser-inspection.md +25 -0
  15. package/bundled-references/maggiedash-booking/CURRENT-STATE.md +128 -10
  16. package/bundled-references/maggiedash-booking/EXECUTION-BOARD.json +4629 -1553
  17. package/bundled-references/maggiedash-booking/HOST-ADAPTER.md +5 -0
  18. package/bundled-references/maggiedash-booking/ORAWELLNESS-INTEGRATION-AUDIT.md +64 -21
  19. package/bundled-references/maggiedash-booking/PRD.md +9 -1
  20. package/bundled-references/maggiedash-booking/PROGRESS.md +244 -2399
  21. package/bundled-references/maggiedash-booking/QA-TEST-PLAN.md +37 -6
  22. package/bundled-references/maggiedash-booking/README.md +23 -6
  23. package/bundled-references/maggiedash-booking/RUNTIME-OPERATIONS.md +64 -8
  24. package/bundled-references/maggiedash-booking/SKILLS-AND-CLI.md +11 -2
  25. package/bundled-references/maggiedash-booking/STRIPE-INTEGRATION.md +66 -2
  26. package/bundled-references/maggiedash-booking/TASK-RUNBOOK.md +1 -1
  27. package/bundled-references/maggiedash-booking/TASKS.md +44 -3
  28. package/bundled-references/maggiedash-booking/VOUCHERS.md +47 -0
  29. package/bundled-references/provider-adapter-contract.md +33 -0
  30. package/bundled-skills/maggie-booking/SKILL.md +8 -0
  31. package/bundled-skills/maggie-clone-to-template/SKILL.md +26 -0
  32. package/bundled-skills/maggie-deployment/SKILL.md +53 -1
  33. package/bundled-skills/maggie-deployment/references/vps.md +41 -0
  34. package/bundled-skills/maggie-design/SKILL.md +99 -0
  35. package/bundled-skills/maggie-feedback/SKILL.md +38 -1
  36. package/bundled-skills/maggie-marketplace/SKILL.md +91 -0
  37. package/bundled-skills/maggie-qa-workflow/SKILL.md +41 -1
  38. package/bundled-skills/maggie-service-booking/SKILL.md +23 -0
  39. package/bundled-skills/maggie-social-share/SKILL.md +37 -5
  40. package/bundled-skills/maggie-social-share/references/queue-and-connections.md +101 -0
  41. package/bundled-skills/maggie-template/SKILL.md +57 -3
  42. package/bundled-skills/maggie-template/references/template-content-v1.example.json +34 -0
  43. package/bundled-tools/clis/maggie_booking.py +199 -26
  44. package/bundled-tools/clis/maggie_booking_vouchers.py +185 -0
  45. package/bundled-tools/clis/maggie_clone_to_template.py +14 -0
  46. package/bundled-tools/clis/maggie_deployment.py +249 -1
  47. package/bundled-tools/clis/maggie_design.py +9 -0
  48. package/bundled-tools/clis/maggie_design_lint.py +277 -0
  49. package/bundled-tools/clis/maggie_feedback.py +106 -3
  50. package/bundled-tools/clis/maggie_marketplace.py +199 -5
  51. package/bundled-tools/clis/maggie_palette.py +280 -0
  52. package/bundled-tools/clis/maggie_qa_workflow.py +156 -1
  53. package/bundled-tools/clis/maggie_social_queue.py +338 -0
  54. package/bundled-tools/clis/maggie_social_share.py +42 -9
  55. package/bundled-tools/clis/maggie_template_package.py +1141 -0
  56. package/package.json +1 -1
  57. package/references/browser-inspection.md +25 -0
  58. package/references/provider-adapter-contract.md +33 -0
package/README-zh-TW.md CHANGED
@@ -29,7 +29,7 @@ npx @topy-ai/maggie init --scope project --agent all
29
29
  npx @topy-ai/maggie doctor --scope project --project .
30
30
  ```
31
31
 
32
- 目前 release 是 `0.7.47`。本版處理 2026-09-26 五條新 feedback:project-scope
32
+ 目前 npm 版本為 `0.7.48`,處理 2026-10-10 的 27 條 hosted feedback(batch 26):Social Share 新增 `adapters`(每個 provider 一組 canonical OAuth scope,LinkedIn 不同 scope 會撤銷舊 token;共用 OAuth client 警告)、`connections`(撤銷或無法解密的 token 標為 `needs_reconnect`,偵測會過期的簽名頭像 URL)、`queue`(slot-based 排程:not-before、最新優先、campaign 輪流與每日上限、DST-safe)與 `campaigns`(idea stage Start gate);Deployment 新增 hash-only `secret-fingerprint`/`secret-parity`、`env-isolation`(本機 `.env` 指向 production database 時警告)、release retention 與 worker-before-enqueue 發布順序;QA 在未明確同意時阻擋對 production API 的寫入情境,並以 `maggie qa cors-preflight` 只用 OPTIONS 檢查每個 HTTP method;Design 新增 `pressable-check`、`layer-check`(Tailwind v4 unlayered CSS)、onboarding wizard/picker 模式與 `maggie-palette-roles-v1` palette generate/validate;Marketplace 加入 screenshot 完整性與像素預算、從 CSS 量測 palette、asset provenance、中性 `displayName`(全部模板已補齊)、template studio、`maggie-template-content-v1` 合約與圖片生成成本/無文字審查 gate;Booking 新增唯讀 Stripe live setup runbook 與 gift voucher lifecycle 合約(`maggie booking voucher-contract --ledger`);Feedback 新增 `improvement` 類型與 `maggie feedback session-summary`。MaggieDash 0.2.11 會保留尚未部署 template 的 outbox email 而不是 dead-letter,並從 ORA host 上游通用修正。本版也包含 Booking 十個 email events 合約與 CLI validator 同步及安全輸出的 `arrivalNote`。前一版 `0.7.47` 處理 2026-09-26 五條新 feedback:project-scope
33
33
  `maggie init` 會建立本地 memory store;context 預設只讀取本 project scope;memory hook
34
34
  在 local Python adapter 不存在時 fallback 到已安裝 CLI;重複 init 保留既有檔案與時間戳;
35
35
  `maggie feedback list` 的 `--project` 可放在子命令前或後。Generated VPS runner 現在記錄
@@ -113,7 +113,7 @@ structure drift 或重複 treatment product 時 fail closed。
113
113
  deployment、memory、feedback 和 MaggieDash。內容先 draft/review,外部寫入、
114
114
  publish 與 production deployment 需要明確確認。
115
115
 
116
- 目前 source tree 的正式 release 是 `0.7.47`。本版完成 2026-09-24 booking feedback batch:Calendar grid/free-slot entry 與 host modal focus-restoration evidence。本版新增 Starter marketplace provisioning plan;本版完成 feedback batches 22、23:加入 declarative browser interaction evidence、design markup/style/content-key gate、compiler source anchoring、entity double-escape protection、`update --help` read-only、noindex hypothetical indexability、可過期 baseline acknowledgement、DOM-only link extraction regression,以及 MaggieDash 0.2.10 的 content override、短期 browser session、CDN-safe public-session cache contracts。authentication 和 isolated dev server 仍由 host 負責。`maggie-booking` workflow、傳統 email/password、Stripe、Resend、public booking flow 及既有安全邊界維持不變;provider-bound video generation 與 transactional delivery 仍記錄在 issue #39,前一批延後功能仍在 issue #38,不會直接成為 active memory。0.7.33 記錄並審查一筆更正回饋;確認 0.7.32 已正確處理 batch index,沒有修改已驗證的 shared behavior。0.7.32 加入 feedback 一基索引支援、MaggieDash panel 的 source/freshness/error evidence、Consent Mode 與實際 write/no-op reconciliation、SEO baseline recapture、sitemap origin rebasing、content-diff scope、migration ledger reconciliation、deployment credential preflight、release provenance/runtime preflight、icon release gate、opt-in blog auto-publish gate,以及 least-privilege VPS deployer。也修復 top-level `maggie feedback` dispatcher parity。0.7.31 加入 update 差異摘要、atomic installer copy、subset install manifest merge,以及 inventory drift 時 doctor non-zero。0.7.30 補上 feedback tracking issue closeout gate 與 batch 14/15 audit ledger。0.7.29 修正 npm package landing page 使用英文 README;0.7.28 加入 versioned Gemini model policy、明確 fallback 與 provenance、bundled-first CLI
116
+ 目前 npm 版本為 `0.7.48`,包含 batch 26 feedback 修正與 Booking email-template 合約/CLI validator 同步。本版完成 2026-09-24 booking feedback batch:Calendar grid/free-slot entry 與 host modal focus-restoration evidence。本版新增 Starter marketplace provisioning plan;本版完成 feedback batches 22、23:加入 declarative browser interaction evidence、design markup/style/content-key gate、compiler source anchoring、entity double-escape protection、`update --help` read-only、noindex hypothetical indexability、可過期 baseline acknowledgement、DOM-only link extraction regression,以及 MaggieDash 0.2.10 的 content override、短期 browser session、CDN-safe public-session cache contracts。authentication 和 isolated dev server 仍由 host 負責。`maggie-booking` workflow、傳統 email/password、Stripe、Resend、public booking flow 及既有安全邊界維持不變;provider-bound video generation 與 transactional delivery 仍記錄在 issue #39,前一批延後功能仍在 issue #38,不會直接成為 active memory。0.7.33 記錄並審查一筆更正回饋;確認 0.7.32 已正確處理 batch index,沒有修改已驗證的 shared behavior。0.7.32 加入 feedback 一基索引支援、MaggieDash panel 的 source/freshness/error evidence、Consent Mode 與實際 write/no-op reconciliation、SEO baseline recapture、sitemap origin rebasing、content-diff scope、migration ledger reconciliation、deployment credential preflight、release provenance/runtime preflight、icon release gate、opt-in blog auto-publish gate,以及 least-privilege VPS deployer。也修復 top-level `maggie feedback` dispatcher parity。0.7.31 加入 update 差異摘要、atomic installer copy、subset install manifest merge,以及 inventory drift 時 doctor non-zero。0.7.30 補上 feedback tracking issue closeout gate 與 batch 14/15 audit ledger。0.7.29 修正 npm package landing page 使用英文 README;0.7.28 加入 versioned Gemini model policy、明確 fallback 與 provenance、bundled-first CLI
117
117
  dispatch、`maggie --version`、feedback batch review 聚合與重複偵測、marketplace enrichment evidence、booking
118
118
  worker/resolver evidence,以及 read-only migration preflight。它也包含 host-owned mobile app surface contract、signed-in
119
119
  camera-state QA、直接 Astro route resolution、correlated feedback batch,以及
package/README.md CHANGED
@@ -89,14 +89,48 @@ Maggie keeps the existing project foundation and asks for decisions before
89
89
  shared routes, analytics, or publishing boundaries change. The current
90
90
  package ships 20 installable skills and a local-first MaggieDash foundation.
91
91
 
92
- The current release is `0.7.47`. Project initialization creates a local Maggie
93
- Memory store, memory contexts default to project scope, and the shared hook
94
- falls back to the installed CLI if project Python tools are absent. Repeated
95
- memory initialization preserves existing files and timestamps. Feedback list
96
- accepts `--project` before or after its subcommand. Generated VPS runners record
97
- their Maggie version and template fingerprint; deployment preflight warns on
98
- stale or unmarked runners, with `maggie deployment --check-runner PATH` for
99
- other locations.
92
+ This package is `0.7.48`. It processes the 27 hosted feedback
93
+ records of 2026-10-10 (batch 26) and includes the Booking email-template
94
+ contract/CLI sync with escaped `arrivalNote` rendering:
95
+
96
+ - Social Share: `adapters` enforces one canonical OAuth scope set per provider
97
+ (LinkedIn revokes earlier tokens on a different scope set) and warns about
98
+ shared OAuth clients; `connections` marks revoked/undecryptable tokens
99
+ `needs_reconnect` and flags expiring signed avatar URLs; `queue` is a
100
+ deterministic slot-based planner (not-before times, newest-first queue,
101
+ campaign round-robin with daily limits, DST-safe); `campaigns` gates the
102
+ idea stage before Start.
103
+ - Deployment: hash-only `secret-fingerprint`/`secret-parity` across hosts,
104
+ `env-isolation` plus a preflight warning when local `.env` points at the
105
+ production database, documented release retention, and worker-before-enqueue
106
+ release ordering.
107
+ - QA: mutating scenarios are blocked against a production API without
108
+ explicit consent, and `maggie qa cors-preflight` checks every HTTP method with
109
+ OPTIONS only.
110
+ - Design: `pressable-check` (nested pressables on React Native Web),
111
+ `layer-check` (unlayered CSS overriding Tailwind v4 utilities), onboarding
112
+ wizard/picker patterns, and the `maggie-palette-roles-v1` contract with
113
+ `maggie design palette generate|validate`.
114
+ - Marketplace/template: package audits for screenshot integrity and pixel
115
+ budget, palettes measured from template CSS, asset provenance, and neutral
116
+ `displayName`s (all catalogue templates backfilled); a template studio
117
+ (viewport × palette with overflow check); the `maggie-template-content-v1`
118
+ contract; and image-generation cost reports with a no-text review gate.
119
+ - Booking: a read-only Stripe live-setup runbook and the provider-neutral gift
120
+ voucher lifecycle contract with `maggie booking voucher-contract --ledger`.
121
+ - Feedback: an `improvement` type (hosted as `feature` + `subtype`) and
122
+ `maggie feedback session-summary`.
123
+ - MaggieDash 0.2.11 holds outbox emails whose template is not yet deployed
124
+ instead of dead-lettering them, and upstreams generic fixes from the ORA host.
125
+
126
+ The 0.7.47 release remains included: project
127
+ initialization creates the repository's Maggie Memory store, memory context
128
+ uses project-scope entries by default, the shared memory hook falls back to
129
+ the installed CLI, repeated memory initialization preserves unchanged
130
+ files, and `maggie feedback list` accepts `--project` before or after the
131
+ subcommand. Generated VPS release runners also record their Maggie version and
132
+ template fingerprint; deployment preflight warns about stale or unmarked
133
+ runners, with `maggie deployment --check-runner PATH` for other locations.
100
134
 
101
135
  The 0.7.46 feedback batch remains included: capability-aware release profiles,
102
136
  bounded deployment-readiness retries, verified Google account/target evidence,
@@ -667,8 +701,8 @@ artifact schemas.
667
701
  Recommended upgrade sequence for the current release:
668
702
 
669
703
  ```bash
670
- npx @topy-ai/maggie@0.7.47 update --scope project --project . --force
671
- npx @topy-ai/maggie@0.7.47 cleanup --scope project --project .
704
+ npx @topy-ai/maggie@0.7.48 update --scope project --project . --force
705
+ npx @topy-ai/maggie@0.7.48 cleanup --scope project --project .
672
706
  ```
673
707
 
674
708
  Maintainers should pass npm credentials through the repository helper, never
@@ -873,11 +907,11 @@ delivery outbox. It shows redacted delivery state and sanitized errors through
873
907
  manages Maggie's server-side transactional delivery queue and audit trail; it
874
908
  does not replace Resend's own domain, audience, campaign, or analytics console.
875
909
 
876
- The Booking browser-evidence gate covers all 15 manager routes at mobile,
877
- tablet, and desktop viewports (45 required screens), including waitlist,
878
- locations, notifications, reports, and audit. A production release still
879
- requires an authenticated HTTPS capture with zero console, request, and
880
- layout errors.
910
+ The Booking browser-evidence gate covers all 17 manager routes at mobile,
911
+ tablet, and desktop viewports (51 required screens), including waitlist,
912
+ locations, notifications, email templates, reports, settings, and audit. A
913
+ production release still requires an authenticated HTTPS capture with zero
914
+ console, request, and layout errors.
881
915
 
882
916
  Compare an existing dashboard before replacing it:
883
917
 
package/bin/maggie.js CHANGED
@@ -99,6 +99,8 @@ Usage:
99
99
  maggie dash structure-validate --model FILE --evidence FILE
100
100
  maggie design progressive-check|css-check|css-cascade-check|style-check --evidence FILE
101
101
  maggie design dash-init|dash-validate|sample-init|sample-validate [options]
102
+ maggie design pressable-check|layer-check --project PATH
103
+ maggie design palette generate --canvas HEX --text HEX --accent HEX | palette validate --palette FILE
102
104
  maggie seo privacy-check --evidence FILE
103
105
  maggie content FILE --source PROVIDER --project PATH --confirm
104
106
  maggie agent-content write --url URL --allowed-origin ORIGIN --token-env ENV --payload FILE
@@ -153,6 +155,8 @@ Usage:
153
155
  maggie service match-pages --project PATH --pages-dir src/pages
154
156
  maggie deployment --project PATH --target vps-with-cloudflare-dns
155
157
  maggie deployment worker-secrets --project PATH --environment staging --required RESEND_API_KEY
158
+ maggie deployment secret-parity --manifest api-1.json --manifest api-2.json --required KEY
159
+ maggie deployment env-isolation --project PATH --production-env .env.production
156
160
  maggie deployment readiness --project PATH
157
161
  maggie deployment parity --project PATH --evidence FILE --output FILE
158
162
  maggie deployment canary --project PATH --asset URL=SHA256 --render-report report.json --output docs/deployment-canary.json
@@ -175,8 +179,8 @@ Usage:
175
179
  maggie memory <init|list|search|context|add|record-error|transition|export> --project PATH
176
180
  maggie localization <extract|plan|generate|preview|validate|review|publish|stale|glossary> [options]
177
181
  maggie seo performance|images|sitemap|indexnow|social-cards|head-tags [options] (sitemap supports strict validate and agent-files)
178
- maggie feedback <collect|preview|batch|batch-review|submit|list> [options]
179
- maggie qa <start|record|summary|export|assertion-audit> [options]
182
+ maggie feedback <collect|preview|batch|batch-review|session-summary|submit|list> [options]
183
+ maggie qa <start|record|summary|export|assertion-audit|cors-preflight> [options]
180
184
  maggie site-audit URL [--crawl] [--access-log FILE] [--require-sitemap-request] [--languages en-GB,es-MX,ja-JP] [--check-hreflang] [--check-internal-links]
181
185
  maggie site-audit URL --crawl --save-baseline FILE --reviewer NAME
182
186
  maggie site-audit URL --crawl --baseline FILE [--reason-all REASON]
@@ -0,0 +1,47 @@
1
+ {
2
+ "$schema": "https://json-schema.org/draft/2020-12/schema",
3
+ "$id": "https://github.com/TOPY-AI-LTD/ai-cmo-skills/blob/main/contracts/maggie-design/palette-roles-v1.schema.json",
4
+ "title": "Maggie template palette role contract",
5
+ "description": "Semantic colour roles for one template: its signature palette plus derived, contrast-safe variants. Generated and validated by `maggie design palette`. Contrast rules (text, accentText and onAccent at 4.5:1) and the variant accent saturation cap are enforced by `maggie design palette validate`, not by this schema.",
6
+ "type": "object",
7
+ "additionalProperties": false,
8
+ "required": ["schemaVersion", "template", "signature", "variants"],
9
+ "properties": {
10
+ "schemaVersion": { "const": "maggie-palette-roles-v1" },
11
+ "template": { "type": ["string", "null"] },
12
+ "signature": {
13
+ "allOf": [
14
+ { "$ref": "#/$defs/palette" },
15
+ { "properties": { "id": { "const": "signature" } } }
16
+ ]
17
+ },
18
+ "variants": { "type": "array", "items": { "$ref": "#/$defs/palette" } }
19
+ },
20
+ "$defs": {
21
+ "hex": { "type": "string", "pattern": "^#[0-9A-Fa-f]{6}$" },
22
+ "palette": {
23
+ "type": "object",
24
+ "required": ["id", "name", "roles"],
25
+ "properties": {
26
+ "id": { "type": "string", "minLength": 1 },
27
+ "name": { "type": "string", "minLength": 1 },
28
+ "roles": {
29
+ "type": "object",
30
+ "additionalProperties": false,
31
+ "required": ["canvas", "panel", "soft", "text", "accent", "accentText", "onAccent", "dark", "deep"],
32
+ "properties": {
33
+ "canvas": { "$ref": "#/$defs/hex", "description": "Page background." },
34
+ "panel": { "$ref": "#/$defs/hex", "description": "Cards and raised surfaces; body text must pass on it." },
35
+ "soft": { "$ref": "#/$defs/hex", "description": "Tinted band or chip background; not for long body copy." },
36
+ "text": { "$ref": "#/$defs/hex", "description": "Body text on canvas and panel." },
37
+ "accent": { "$ref": "#/$defs/hex", "description": "Buttons and highlights (fills)." },
38
+ "accentText": { "$ref": "#/$defs/hex", "description": "Accent-coloured text and links on canvas." },
39
+ "onAccent": { "$ref": "#/$defs/hex", "description": "Text placed on an accent fill." },
40
+ "dark": { "$ref": "#/$defs/hex", "description": "Dark band background." },
41
+ "deep": { "$ref": "#/$defs/hex", "description": "Deepest band, footer or overlay." }
42
+ }
43
+ }
44
+ }
45
+ }
46
+ }
47
+ }
@@ -0,0 +1,103 @@
1
+ {
2
+ "$schema": "https://json-schema.org/draft/2020-12/schema",
3
+ "$id": "https://github.com/TOPY-AI-LTD/ai-cmo-skills/blob/main/contracts/maggie-marketplace/template-content-v1.schema.json",
4
+ "title": "Maggie template content contract",
5
+ "description": "Neutral business content a marketplace template renders when exported as a data-driven component, so one design serves many businesses from their own data. Palette roles come from maggie-palette-roles-v1 and are emitted as --maggie-<role> CSS variables. Business rules (sample paths resolve, reviews carry a source or sample=true, hours are HH:MM) are enforced by `maggie_marketplace.py content-validate`.",
6
+ "type": "object",
7
+ "required": ["schemaVersion", "brand", "contact", "hero", "categories", "about", "gallery", "reviews", "hours", "faqs"],
8
+ "properties": {
9
+ "schemaVersion": { "const": "maggie-template-content-v1" },
10
+ "brand": {
11
+ "type": "object",
12
+ "required": ["name"],
13
+ "properties": {
14
+ "name": { "type": "string", "minLength": 1 },
15
+ "tagline": { "type": ["string", "null"] },
16
+ "logo": { "$ref": "#/$defs/image" }
17
+ }
18
+ },
19
+ "contact": {
20
+ "type": "object",
21
+ "properties": {
22
+ "phone": { "type": ["string", "null"] },
23
+ "email": { "type": ["string", "null"] },
24
+ "address": { "type": ["string", "null"] },
25
+ "bookingUrl": { "type": ["string", "null"] }
26
+ }
27
+ },
28
+ "hero": {
29
+ "type": "object",
30
+ "required": ["headline"],
31
+ "properties": {
32
+ "headline": { "type": "string", "minLength": 1 },
33
+ "subheadline": { "type": ["string", "null"] },
34
+ "image": { "$ref": "#/$defs/image" },
35
+ "cta": { "type": "object", "properties": { "label": { "type": "string" }, "href": { "type": "string" } } }
36
+ }
37
+ },
38
+ "categories": {
39
+ "type": "array",
40
+ "items": {
41
+ "type": "object",
42
+ "required": ["name", "services"],
43
+ "properties": {
44
+ "name": { "type": "string", "minLength": 1 },
45
+ "description": { "type": ["string", "null"] },
46
+ "services": {
47
+ "type": "array",
48
+ "items": {
49
+ "type": "object",
50
+ "required": ["name"],
51
+ "properties": {
52
+ "name": { "type": "string", "minLength": 1 },
53
+ "description": { "type": ["string", "null"] },
54
+ "price": { "type": ["number", "null"], "minimum": 0 },
55
+ "currency": { "type": "string", "default": "GBP" },
56
+ "durationMinutes": { "type": ["integer", "null"], "minimum": 1 },
57
+ "bookingRef": { "type": ["string", "null"], "description": "Host booking/catalogue identifier, e.g. a MaggieDash Booking service id." }
58
+ }
59
+ }
60
+ }
61
+ }
62
+ }
63
+ },
64
+ "about": { "type": "object", "properties": { "heading": { "type": ["string", "null"] }, "body": { "type": ["string", "null"] }, "image": { "$ref": "#/$defs/image" } } },
65
+ "gallery": { "type": "array", "items": { "$ref": "#/$defs/image" } },
66
+ "reviews": {
67
+ "type": "array",
68
+ "items": {
69
+ "type": "object",
70
+ "required": ["quote"],
71
+ "properties": {
72
+ "quote": { "type": "string" },
73
+ "author": { "type": ["string", "null"] },
74
+ "rating": { "type": ["number", "null"], "minimum": 0, "maximum": 5 },
75
+ "source": { "type": ["string", "null"], "description": "Where the real review came from; required unless sample is true." },
76
+ "sample": { "type": "boolean" }
77
+ }
78
+ }
79
+ },
80
+ "hours": {
81
+ "type": "array",
82
+ "items": {
83
+ "type": "object",
84
+ "required": ["day"],
85
+ "properties": {
86
+ "day": { "enum": ["mon", "tue", "wed", "thu", "fri", "sat", "sun"] },
87
+ "opens": { "type": "string", "pattern": "^\\d{2}:\\d{2}$" },
88
+ "closes": { "type": "string", "pattern": "^\\d{2}:\\d{2}$" },
89
+ "closed": { "type": "boolean" }
90
+ }
91
+ }
92
+ },
93
+ "faqs": { "type": "array", "items": { "type": "object", "required": ["question", "answer"], "properties": { "question": { "type": "string" }, "answer": { "type": "string" } } } },
94
+ "samples": { "type": "array", "items": { "type": "string" }, "description": "Dotted content paths that still hold template sample copy the owner must replace (e.g. hero.headline, reviews.0)." },
95
+ "palette": { "type": "object", "description": "One maggie-palette-roles-v1 palette (id, name, roles)." }
96
+ },
97
+ "$defs": {
98
+ "image": {
99
+ "type": ["object", "null"],
100
+ "properties": { "src": { "type": "string" }, "alt": { "type": "string" } }
101
+ }
102
+ }
103
+ }
@@ -0,0 +1,21 @@
1
+ {
2
+ "$schema": "https://json-schema.org/draft/2020-12/schema",
3
+ "$id": "https://maggiedash.topy.ai/contracts/booking-browser-evidence-v1.json",
4
+ "title": "MaggieDash Booking production browser evidence v1",
5
+ "type": "object",
6
+ "required": ["schemaVersion", "baseUrl", "generatedAt", "viewports", "screens", "consoleErrors", "failedRequests", "layoutErrors"],
7
+ "properties": {
8
+ "schemaVersion": { "const": "maggiedash-booking-browser-evidence.v1" },
9
+ "baseUrl": { "type": "string", "pattern": "^https://" },
10
+ "generatedAt": { "type": "string", "format": "date-time" },
11
+ "version": { "type": "string" },
12
+ "viewports": { "type": "array", "minItems": 3, "items": { "type": "object", "required": ["name", "width", "height"] } },
13
+ "screens": { "type": "array", "minItems": 51, "items": { "type": "object", "required": ["route", "viewport", "httpStatus", "screenshot", "ready"] } },
14
+ "consoleErrors": { "type": "array", "items": { "type": "string" } },
15
+ "failedRequests": { "type": "array", "items": { "type": "string" } },
16
+ "layoutErrors": { "type": "array", "items": { "type": "string" } },
17
+ "notes": { "type": "array", "items": { "type": "string" } }
18
+ },
19
+ "x-required-routes": ["/_maggie/booking/", "/_maggie/booking/calendar", "/_maggie/booking/bookings", "/_maggie/booking/customers", "/_maggie/booking/waitlist", "/_maggie/booking/locations", "/_maggie/booking/catalog", "/_maggie/booking/packages", "/_maggie/booking/staff", "/_maggie/booking/resources", "/_maggie/booking/schedule", "/_maggie/booking/payments", "/_maggie/booking/notifications", "/_maggie/booking/email-templates", "/_maggie/booking/reports", "/_maggie/booking/settings", "/_maggie/booking/audit"],
20
+ "x-required-viewports": [{"name":"mobile","width":390,"height":844},{"name":"tablet","width":768,"height":1024},{"name":"desktop","width":1440,"height":1000}]
21
+ }
@@ -0,0 +1,191 @@
1
+ {
2
+ "$schema": "https://json-schema.org/draft/2020-12/schema",
3
+ "$id": "https://maggiedash.topy.ai/contracts/booking-browser-evidence-v2.json",
4
+ "title": "MaggieDash Booking production browser evidence v2",
5
+ "type": "object",
6
+ "required": [
7
+ "schemaVersion",
8
+ "baseUrl",
9
+ "generatedAt",
10
+ "viewports",
11
+ "screens",
12
+ "consoleErrors",
13
+ "failedRequests",
14
+ "layoutErrors"
15
+ ],
16
+ "properties": {
17
+ "schemaVersion": {
18
+ "const": "maggiedash-booking-browser-evidence.v2"
19
+ },
20
+ "baseUrl": {
21
+ "type": "string",
22
+ "pattern": "^https://"
23
+ },
24
+ "generatedAt": {
25
+ "type": "string",
26
+ "format": "date-time"
27
+ },
28
+ "version": {
29
+ "type": "string"
30
+ },
31
+ "viewports": {
32
+ "type": "array",
33
+ "minItems": 3,
34
+ "items": {
35
+ "type": "object",
36
+ "required": [
37
+ "name",
38
+ "width",
39
+ "height"
40
+ ]
41
+ }
42
+ },
43
+ "screens": {
44
+ "type": "array",
45
+ "minItems": 51,
46
+ "items": {
47
+ "type": "object",
48
+ "required": [
49
+ "route",
50
+ "viewport",
51
+ "httpStatus",
52
+ "finalPath",
53
+ "heading",
54
+ "screenshot",
55
+ "ready"
56
+ ],
57
+ "properties": {
58
+ "route": {
59
+ "type": "string",
60
+ "enum": [
61
+ "/_maggie/booking/",
62
+ "/_maggie/booking/calendar",
63
+ "/_maggie/booking/bookings",
64
+ "/_maggie/booking/customers",
65
+ "/_maggie/booking/waitlist",
66
+ "/_maggie/booking/locations",
67
+ "/_maggie/booking/catalog",
68
+ "/_maggie/booking/packages",
69
+ "/_maggie/booking/staff",
70
+ "/_maggie/booking/resources",
71
+ "/_maggie/booking/schedule",
72
+ "/_maggie/booking/payments",
73
+ "/_maggie/booking/notifications",
74
+ "/_maggie/booking/email-templates",
75
+ "/_maggie/booking/reports",
76
+ "/_maggie/booking/settings",
77
+ "/_maggie/booking/audit"
78
+ ]
79
+ },
80
+ "viewport": {
81
+ "type": "string",
82
+ "enum": [
83
+ "mobile",
84
+ "tablet",
85
+ "desktop"
86
+ ]
87
+ },
88
+ "httpStatus": {
89
+ "type": "integer",
90
+ "minimum": 200,
91
+ "maximum": 399
92
+ },
93
+ "finalPath": {
94
+ "type": "string",
95
+ "pattern": "^/_maggie/booking(?:/|$)"
96
+ },
97
+ "heading": {
98
+ "type": "string",
99
+ "minLength": 1
100
+ },
101
+ "screenshot": {
102
+ "type": "string",
103
+ "minLength": 1
104
+ },
105
+ "ready": {
106
+ "const": true
107
+ }
108
+ }
109
+ }
110
+ },
111
+ "consoleErrors": {
112
+ "type": "array",
113
+ "items": {
114
+ "type": "string"
115
+ }
116
+ },
117
+ "failedRequests": {
118
+ "type": "array",
119
+ "items": {
120
+ "type": "string"
121
+ }
122
+ },
123
+ "layoutErrors": {
124
+ "type": "array",
125
+ "items": {
126
+ "type": "string"
127
+ }
128
+ },
129
+ "notes": {
130
+ "type": "array",
131
+ "items": {
132
+ "type": "string"
133
+ }
134
+ }
135
+ },
136
+ "x-required-routes": [
137
+ "/_maggie/booking/",
138
+ "/_maggie/booking/calendar",
139
+ "/_maggie/booking/bookings",
140
+ "/_maggie/booking/customers",
141
+ "/_maggie/booking/waitlist",
142
+ "/_maggie/booking/locations",
143
+ "/_maggie/booking/catalog",
144
+ "/_maggie/booking/packages",
145
+ "/_maggie/booking/staff",
146
+ "/_maggie/booking/resources",
147
+ "/_maggie/booking/schedule",
148
+ "/_maggie/booking/payments",
149
+ "/_maggie/booking/notifications",
150
+ "/_maggie/booking/email-templates",
151
+ "/_maggie/booking/reports",
152
+ "/_maggie/booking/settings",
153
+ "/_maggie/booking/audit"
154
+ ],
155
+ "x-required-viewports": [
156
+ {
157
+ "name": "mobile",
158
+ "width": 390,
159
+ "height": 844
160
+ },
161
+ {
162
+ "name": "tablet",
163
+ "width": 768,
164
+ "height": 1024
165
+ },
166
+ {
167
+ "name": "desktop",
168
+ "width": 1440,
169
+ "height": 1000
170
+ }
171
+ ],
172
+ "x-required-headings": {
173
+ "/_maggie/booking/": "Overview",
174
+ "/_maggie/booking/calendar": "Calendar",
175
+ "/_maggie/booking/bookings": "Bookings",
176
+ "/_maggie/booking/customers": "Customers",
177
+ "/_maggie/booking/waitlist": "Waitlist",
178
+ "/_maggie/booking/locations": "Locations",
179
+ "/_maggie/booking/catalog": "Catalogue",
180
+ "/_maggie/booking/packages": "Packages",
181
+ "/_maggie/booking/staff": "Staff",
182
+ "/_maggie/booking/resources": "Resources",
183
+ "/_maggie/booking/schedule": "Schedule",
184
+ "/_maggie/booking/payments": "Payments",
185
+ "/_maggie/booking/notifications": "Notifications",
186
+ "/_maggie/booking/email-templates": "Email templates",
187
+ "/_maggie/booking/reports": "Reports",
188
+ "/_maggie/booking/settings": "Settings",
189
+ "/_maggie/booking/audit": "Audit"
190
+ }
191
+ }
@@ -11,16 +11,18 @@
11
11
  },
12
12
  "roles": ["owner", "admin", "manager"],
13
13
  "events": [
14
- { "id": "booking.confirmed", "variables": ["customerName", "serviceName", "when", "locationName", "bookingId", "manageUrl", "siteName"] },
14
+ { "id": "booking.confirmed", "variables": ["customerName", "serviceName", "when", "locationName", "bookingId", "manageUrl", "siteName", "arrivalNote"] },
15
15
  { "id": "booking.rescheduled", "variables": ["customerName", "serviceName", "when", "locationName", "bookingId", "manageUrl", "siteName"] },
16
16
  { "id": "booking.cancelled", "variables": ["customerName", "serviceName", "when", "locationName", "bookingId", "reason", "siteName"] },
17
17
  { "id": "booking.reminder", "variables": ["customerName", "serviceName", "when", "locationName", "bookingId", "manageUrl", "siteName"] },
18
18
  { "id": "payment.action_required", "variables": ["customerName", "serviceName", "bookingId", "actionUrl", "siteName"] },
19
19
  { "id": "payment.refunded", "variables": ["customerName", "serviceName", "bookingId", "siteName"] },
20
+ { "id": "payment.no_show_fee", "variables": ["customerName", "serviceName", "bookingId", "amount", "siteName"] },
20
21
  { "id": "package.purchase.confirmed", "variables": ["customerName", "packageName", "amount", "expiresAt", "siteName"] },
21
22
  { "id": "package.purchase.refunded", "variables": ["customerName", "packageName", "amount", "siteName"] },
22
23
  { "id": "booking.waitlist.available", "variables": ["customerName", "serviceName", "when", "locationName", "bookingUrl", "siteName"] }
23
24
  ],
25
+ "variables": ["customerName", "serviceName", "when", "locationName", "bookingId", "manageUrl", "bookingUrl", "reason", "actionUrl", "packageName", "amount", "expiresAt", "siteName", "arrivalNote"],
24
26
  "endpointIds": ["booking.email-templates.read", "booking.email-templates.draft", "booking.email-templates.publish", "booking.email-templates.rollback"],
25
27
  "canonicalRoutes": {
26
28
  "booking.email-templates.read": "GET /email-templates.json",
@@ -0,0 +1,85 @@
1
+ {
2
+ "$schema": "https://json-schema.org/draft/2020-12/schema",
3
+ "$id": "https://maggiedash.topy.ai/contracts/booking-voucher-lifecycle-v1.json",
4
+ "title": "MaggieDash Booking gift voucher lifecycle v1",
5
+ "schemaVersion": "maggiedash-booking-voucher-lifecycle.v1",
6
+ "status": "contract",
7
+ "runtime": {
8
+ "owner": "host",
9
+ "maggieDashRuntime": false,
10
+ "note": "This contract fixes the provider-neutral voucher lifecycle. MaggieDash does not ship a voucher runtime in this release; a host implements it and proves it with a sanitized ledger fixture."
11
+ },
12
+ "apiPrefix": "/api/maggie/booking/vouchers.json",
13
+ "auth": { "managerSession": "host-session-cookie", "emailPassword": true, "passkeys": false },
14
+ "permissions": ["vouchers.read", "vouchers.sell", "vouchers.redeem", "vouchers.void", "vouchers.refund"],
15
+ "money": { "unit": "minor", "integerOnly": true, "singleCurrencyPerVoucher": true },
16
+ "channels": {
17
+ "online": {
18
+ "funding": "provider-payment",
19
+ "issueAfter": "verified payment success webhook",
20
+ "provider": "stripe",
21
+ "providerObjects": ["checkout_sessions", "payment_intents", "refunds"],
22
+ "nativeGiftCards": false
23
+ },
24
+ "till": {
25
+ "funding": "recorded-in-shop-payment",
26
+ "paymentMethods": ["cash", "card-terminal", "external"],
27
+ "requiredPermission": "vouchers.sell"
28
+ }
29
+ },
30
+ "codeFormat": {
31
+ "online": {
32
+ "pattern": "^[A-Z]{2,4}-[A-Z2-9]{4}-[A-Z2-9]{4}-[A-Z2-9]{4}$",
33
+ "alphabet": "ABCDEFGHJKLMNPQRSTUVWXYZ23456789",
34
+ "check": "hmac-sha256",
35
+ "checkSegment": "last segment is a truncated HMAC of the body under a server-only secret; verify in constant time before any database lookup"
36
+ },
37
+ "till": {
38
+ "pattern": "^[A-Z]{1,4}[0-9]{6,10}$",
39
+ "check": "luhn",
40
+ "checkSegment": "final digit is a Luhn check digit so mistyped printed codes fail before lookup"
41
+ },
42
+ "storage": "store only codeHash and codeLast4; never persist or return the full code after delivery"
43
+ },
44
+ "states": ["pending_payment", "active", "exhausted", "expired", "voided", "refunded"],
45
+ "ledger": {
46
+ "appendOnly": true,
47
+ "entryTypes": ["issue", "redeem", "undo_redeem", "void", "expire", "refund"],
48
+ "balanceRule": "balance = issue - redeem + undo_redeem - refund; it never becomes negative",
49
+ "fields": ["id", "voucherId", "type", "amount", "at", "actorId", "idempotencyKey", "reverses", "bookingId", "paymentRef", "refundMethod", "reason"]
50
+ },
51
+ "rules": {
52
+ "issue": "exactly one issue entry, first in the ledger, equal to faceValue; online vouchers stay pending_payment until the verified payment webhook",
53
+ "partialRedemption": "a redemption may be any positive amount up to the remaining balance; the remainder stays redeemable",
54
+ "undo": "undo_redeem reverses exactly one earlier redeem entry by id, for the same amount, at most once, and never after void",
55
+ "void": "void requires a reason and blocks every later redemption, undo, and refund; the remaining balance is reported but unusable",
56
+ "expiry": "no redemption at or after expiresAt; an expire entry records the unused balance without changing the ledger history",
57
+ "refund": "refund amount is capped by the remaining balance and by the funded amount minus earlier refunds; online refunds reference the original provider payment; till refunds record refundMethod",
58
+ "fullRefund": "a refund that brings the balance to zero before any redemption moves the voucher to refunded"
59
+ },
60
+ "notifications": [
61
+ { "id": "voucher.purchase.confirmed", "recipient": "buyer", "variables": ["customerName", "amount", "voucherLast4", "expiresAt", "siteName"] },
62
+ { "id": "voucher.delivered", "recipient": "recipient", "variables": ["recipientName", "senderName", "message", "amount", "voucherCode", "expiresAt", "redeemUrl", "siteName"] },
63
+ { "id": "voucher.redeemed", "recipient": "buyer-or-recipient", "variables": ["amount", "remainingBalance", "voucherLast4", "siteName"] },
64
+ { "id": "voucher.refunded", "recipient": "buyer", "variables": ["customerName", "amount", "voucherLast4", "siteName"] },
65
+ { "id": "voucher.expiry_reminder", "recipient": "recipient", "variables": ["recipientName", "remainingBalance", "expiresAt", "redeemUrl", "siteName"] }
66
+ ],
67
+ "endpointIds": ["booking.vouchers.read", "booking.vouchers.sell", "booking.vouchers.redeem", "booking.vouchers.undo", "booking.vouchers.void", "booking.vouchers.refund"],
68
+ "canonicalRoutes": {
69
+ "booking.vouchers.read": "GET /vouchers.json",
70
+ "booking.vouchers.sell": "POST /vouchers.json?action=sell",
71
+ "booking.vouchers.redeem": "POST /vouchers.json?action=redeem",
72
+ "booking.vouchers.undo": "POST /vouchers.json?action=undo",
73
+ "booking.vouchers.void": "POST /vouchers.json?action=void",
74
+ "booking.vouchers.refund": "POST /vouchers.json?action=refund"
75
+ },
76
+ "policy": {
77
+ "tenantScoped": true,
78
+ "auditRequired": true,
79
+ "idempotencyRequiredForMutations": true,
80
+ "fullCodeOnlyInDeliveryEmail": true,
81
+ "providerCredentialsRemainServerOnly": true,
82
+ "expiryPolicyDeclaredByHost": true
83
+ },
84
+ "ledgerFixtureSchemaVersion": "maggiedash-booking-voucher-ledger.v1"
85
+ }