ggcheckout-mcp 0.2.4 → 0.4.0

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 (208) hide show
  1. package/CHANGELOG.md +252 -0
  2. package/README.md +217 -47
  3. package/dist/__e2e__/setup.js +1 -1
  4. package/dist/__e2e__/setup.js.map +1 -1
  5. package/dist/adapters/inbound/tools/billing.tools.d.ts +1 -1
  6. package/dist/adapters/inbound/tools/billing.tools.d.ts.map +1 -1
  7. package/dist/adapters/inbound/tools/billing.tools.js +32 -6
  8. package/dist/adapters/inbound/tools/billing.tools.js.map +1 -1
  9. package/dist/adapters/inbound/tools/checkout.tools.d.ts.map +1 -1
  10. package/dist/adapters/inbound/tools/checkout.tools.js +15 -8
  11. package/dist/adapters/inbound/tools/checkout.tools.js.map +1 -1
  12. package/dist/adapters/inbound/tools/discount.tools.js +1 -1
  13. package/dist/adapters/inbound/tools/discount.tools.js.map +1 -1
  14. package/dist/adapters/inbound/tools/funnel.tools.d.ts.map +1 -1
  15. package/dist/adapters/inbound/tools/funnel.tools.js +89 -51
  16. package/dist/adapters/inbound/tools/funnel.tools.js.map +1 -1
  17. package/dist/adapters/inbound/tools/gateway.tools.d.ts.map +1 -1
  18. package/dist/adapters/inbound/tools/gateway.tools.js +11 -3
  19. package/dist/adapters/inbound/tools/gateway.tools.js.map +1 -1
  20. package/dist/adapters/inbound/tools/members-area.tools.d.ts.map +1 -1
  21. package/dist/adapters/inbound/tools/members-area.tools.js +263 -31
  22. package/dist/adapters/inbound/tools/members-area.tools.js.map +1 -1
  23. package/dist/adapters/inbound/tools/payment.tools.d.ts.map +1 -1
  24. package/dist/adapters/inbound/tools/payment.tools.js +9 -3
  25. package/dist/adapters/inbound/tools/payment.tools.js.map +1 -1
  26. package/dist/adapters/inbound/tools/product.tools.d.ts.map +1 -1
  27. package/dist/adapters/inbound/tools/product.tools.js +115 -29
  28. package/dist/adapters/inbound/tools/product.tools.js.map +1 -1
  29. package/dist/adapters/inbound/tools/rewards.tools.d.ts.map +1 -1
  30. package/dist/adapters/inbound/tools/rewards.tools.js +6 -2
  31. package/dist/adapters/inbound/tools/rewards.tools.js.map +1 -1
  32. package/dist/adapters/inbound/tools/shipping.tools.js +1 -1
  33. package/dist/adapters/inbound/tools/shipping.tools.js.map +1 -1
  34. package/dist/adapters/inbound/tools/store.tools.d.ts.map +1 -1
  35. package/dist/adapters/inbound/tools/store.tools.js +302 -25
  36. package/dist/adapters/inbound/tools/store.tools.js.map +1 -1
  37. package/dist/adapters/inbound/tools/telegram.tools.d.ts.map +1 -1
  38. package/dist/adapters/inbound/tools/telegram.tools.js +8 -1
  39. package/dist/adapters/inbound/tools/telegram.tools.js.map +1 -1
  40. package/dist/adapters/inbound/tools/webhook.tools.d.ts.map +1 -1
  41. package/dist/adapters/inbound/tools/webhook.tools.js +17 -8
  42. package/dist/adapters/inbound/tools/webhook.tools.js.map +1 -1
  43. package/dist/adapters/inbound/tools/whatsapp.tools.d.ts.map +1 -1
  44. package/dist/adapters/inbound/tools/whatsapp.tools.js +3 -1
  45. package/dist/adapters/inbound/tools/whatsapp.tools.js.map +1 -1
  46. package/dist/adapters/outbound/auth.api.d.ts +7 -0
  47. package/dist/adapters/outbound/auth.api.d.ts.map +1 -1
  48. package/dist/adapters/outbound/auth.api.js +18 -2
  49. package/dist/adapters/outbound/auth.api.js.map +1 -1
  50. package/dist/adapters/outbound/billing.api.d.ts +25 -8
  51. package/dist/adapters/outbound/billing.api.d.ts.map +1 -1
  52. package/dist/adapters/outbound/billing.api.js +86 -3
  53. package/dist/adapters/outbound/billing.api.js.map +1 -1
  54. package/dist/adapters/outbound/checkout.api.d.ts +4 -4
  55. package/dist/adapters/outbound/checkout.api.d.ts.map +1 -1
  56. package/dist/adapters/outbound/checkout.api.js +26 -10
  57. package/dist/adapters/outbound/checkout.api.js.map +1 -1
  58. package/dist/adapters/outbound/checkout.api.test.js +58 -11
  59. package/dist/adapters/outbound/checkout.api.test.js.map +1 -1
  60. package/dist/adapters/outbound/funnel.api.d.ts +3 -1
  61. package/dist/adapters/outbound/funnel.api.d.ts.map +1 -1
  62. package/dist/adapters/outbound/funnel.api.js +25 -9
  63. package/dist/adapters/outbound/funnel.api.js.map +1 -1
  64. package/dist/adapters/outbound/http-client.d.ts +12 -0
  65. package/dist/adapters/outbound/http-client.d.ts.map +1 -1
  66. package/dist/adapters/outbound/http-client.js +63 -12
  67. package/dist/adapters/outbound/http-client.js.map +1 -1
  68. package/dist/adapters/outbound/http-client.test.js +2 -2
  69. package/dist/adapters/outbound/http-client.test.js.map +1 -1
  70. package/dist/adapters/outbound/members-area.api.d.ts +55 -2
  71. package/dist/adapters/outbound/members-area.api.d.ts.map +1 -1
  72. package/dist/adapters/outbound/members-area.api.js +89 -1
  73. package/dist/adapters/outbound/members-area.api.js.map +1 -1
  74. package/dist/adapters/outbound/payment.api.d.ts +6 -0
  75. package/dist/adapters/outbound/payment.api.d.ts.map +1 -1
  76. package/dist/adapters/outbound/payment.api.js +17 -3
  77. package/dist/adapters/outbound/payment.api.js.map +1 -1
  78. package/dist/adapters/outbound/product.api.d.ts +39 -7
  79. package/dist/adapters/outbound/product.api.d.ts.map +1 -1
  80. package/dist/adapters/outbound/product.api.js +57 -15
  81. package/dist/adapters/outbound/product.api.js.map +1 -1
  82. package/dist/adapters/outbound/product.api.test.js +14 -1
  83. package/dist/adapters/outbound/product.api.test.js.map +1 -1
  84. package/dist/adapters/outbound/rewards.api.d.ts +5 -1
  85. package/dist/adapters/outbound/rewards.api.d.ts.map +1 -1
  86. package/dist/adapters/outbound/rewards.api.js +5 -1
  87. package/dist/adapters/outbound/rewards.api.js.map +1 -1
  88. package/dist/adapters/outbound/signed-upload.d.ts +10 -0
  89. package/dist/adapters/outbound/signed-upload.d.ts.map +1 -0
  90. package/dist/adapters/outbound/signed-upload.js +29 -0
  91. package/dist/adapters/outbound/signed-upload.js.map +1 -0
  92. package/dist/adapters/outbound/store.api.d.ts +37 -1
  93. package/dist/adapters/outbound/store.api.d.ts.map +1 -1
  94. package/dist/adapters/outbound/store.api.js +88 -7
  95. package/dist/adapters/outbound/store.api.js.map +1 -1
  96. package/dist/adapters/outbound/store.api.test.js +62 -0
  97. package/dist/adapters/outbound/store.api.test.js.map +1 -1
  98. package/dist/adapters/outbound/telegram.api.d.ts +5 -0
  99. package/dist/adapters/outbound/telegram.api.d.ts.map +1 -1
  100. package/dist/adapters/outbound/telegram.api.js +7 -2
  101. package/dist/adapters/outbound/telegram.api.js.map +1 -1
  102. package/dist/adapters/outbound/whatsapp.api.d.ts +5 -0
  103. package/dist/adapters/outbound/whatsapp.api.d.ts.map +1 -1
  104. package/dist/adapters/outbound/whatsapp.api.js +20 -3
  105. package/dist/adapters/outbound/whatsapp.api.js.map +1 -1
  106. package/dist/core/ports/billing.port.d.ts +8 -8
  107. package/dist/core/ports/billing.port.d.ts.map +1 -1
  108. package/dist/core/ports/checkout.port.d.ts +4 -4
  109. package/dist/core/ports/checkout.port.d.ts.map +1 -1
  110. package/dist/core/ports/funnel.port.d.ts +4 -1
  111. package/dist/core/ports/funnel.port.d.ts.map +1 -1
  112. package/dist/core/ports/members-area.port.d.ts +42 -1
  113. package/dist/core/ports/members-area.port.d.ts.map +1 -1
  114. package/dist/core/ports/product.port.d.ts +22 -7
  115. package/dist/core/ports/product.port.d.ts.map +1 -1
  116. package/dist/core/ports/rewards.port.d.ts +0 -1
  117. package/dist/core/ports/rewards.port.d.ts.map +1 -1
  118. package/dist/core/ports/store.port.d.ts +36 -1
  119. package/dist/core/ports/store.port.d.ts.map +1 -1
  120. package/dist/core/services/billing.service.d.ts +14 -7
  121. package/dist/core/services/billing.service.d.ts.map +1 -1
  122. package/dist/core/services/billing.service.js +42 -2
  123. package/dist/core/services/billing.service.js.map +1 -1
  124. package/dist/core/services/checkout.service.d.ts +21 -2
  125. package/dist/core/services/checkout.service.d.ts.map +1 -1
  126. package/dist/core/services/checkout.service.js +102 -14
  127. package/dist/core/services/checkout.service.js.map +1 -1
  128. package/dist/core/services/checkout.service.test.js +124 -67
  129. package/dist/core/services/checkout.service.test.js.map +1 -1
  130. package/dist/core/services/funnel.service.d.ts +8 -1
  131. package/dist/core/services/funnel.service.d.ts.map +1 -1
  132. package/dist/core/services/funnel.service.js +21 -1
  133. package/dist/core/services/funnel.service.js.map +1 -1
  134. package/dist/core/services/funnel.service.test.d.ts +2 -0
  135. package/dist/core/services/funnel.service.test.d.ts.map +1 -0
  136. package/dist/core/services/funnel.service.test.js +82 -0
  137. package/dist/core/services/funnel.service.test.js.map +1 -0
  138. package/dist/core/services/members-area.service.d.ts +48 -2
  139. package/dist/core/services/members-area.service.d.ts.map +1 -1
  140. package/dist/core/services/members-area.service.js +35 -1
  141. package/dist/core/services/members-area.service.js.map +1 -1
  142. package/dist/core/services/product.service.d.ts +95 -6
  143. package/dist/core/services/product.service.d.ts.map +1 -1
  144. package/dist/core/services/product.service.js +280 -13
  145. package/dist/core/services/product.service.js.map +1 -1
  146. package/dist/core/services/product.service.test.js +80 -0
  147. package/dist/core/services/product.service.test.js.map +1 -1
  148. package/dist/core/services/rewards.service.d.ts +0 -1
  149. package/dist/core/services/rewards.service.d.ts.map +1 -1
  150. package/dist/core/services/rewards.service.js +0 -1
  151. package/dist/core/services/rewards.service.js.map +1 -1
  152. package/dist/core/services/store.service.d.ts +46 -1
  153. package/dist/core/services/store.service.d.ts.map +1 -1
  154. package/dist/core/services/store.service.js +115 -0
  155. package/dist/core/services/store.service.js.map +1 -1
  156. package/dist/core/services/store.service.test.d.ts +2 -0
  157. package/dist/core/services/store.service.test.d.ts.map +1 -0
  158. package/dist/core/services/store.service.test.js +62 -0
  159. package/dist/core/services/store.service.test.js.map +1 -0
  160. package/dist/core/types/billing.d.ts +60 -0
  161. package/dist/core/types/billing.d.ts.map +1 -1
  162. package/dist/core/types/checkout.d.ts +43 -4
  163. package/dist/core/types/checkout.d.ts.map +1 -1
  164. package/dist/core/types/funnel.d.ts +57 -10
  165. package/dist/core/types/funnel.d.ts.map +1 -1
  166. package/dist/core/types/members-area.d.ts +69 -0
  167. package/dist/core/types/members-area.d.ts.map +1 -1
  168. package/dist/core/types/payment.d.ts +10 -1
  169. package/dist/core/types/payment.d.ts.map +1 -1
  170. package/dist/core/types/product.d.ts +92 -11
  171. package/dist/core/types/product.d.ts.map +1 -1
  172. package/dist/core/types/rewards.d.ts +4 -0
  173. package/dist/core/types/rewards.d.ts.map +1 -1
  174. package/dist/core/types/store.d.ts +82 -0
  175. package/dist/core/types/store.d.ts.map +1 -1
  176. package/dist/core/types/telegram.d.ts +3 -1
  177. package/dist/core/types/telegram.d.ts.map +1 -1
  178. package/dist/core/types/telegram.js +1 -1
  179. package/dist/core/types/telegram.js.map +1 -1
  180. package/dist/index.js +6 -4
  181. package/dist/index.js.map +1 -1
  182. package/dist/shared/errors.d.ts +11 -1
  183. package/dist/shared/errors.d.ts.map +1 -1
  184. package/dist/shared/errors.js +15 -2
  185. package/dist/shared/errors.js.map +1 -1
  186. package/dist/shared/external-offer-snippet.d.ts +25 -0
  187. package/dist/shared/external-offer-snippet.d.ts.map +1 -0
  188. package/dist/shared/external-offer-snippet.js +114 -0
  189. package/dist/shared/external-offer-snippet.js.map +1 -0
  190. package/dist/shared/local-file.d.ts +32 -0
  191. package/dist/shared/local-file.d.ts.map +1 -0
  192. package/dist/shared/local-file.js +92 -0
  193. package/dist/shared/local-file.js.map +1 -0
  194. package/dist/shared/merge.d.ts +6 -0
  195. package/dist/shared/merge.d.ts.map +1 -0
  196. package/dist/shared/merge.js +22 -0
  197. package/dist/shared/merge.js.map +1 -0
  198. package/dist/shared/sanitizer.d.ts +7 -0
  199. package/dist/shared/sanitizer.d.ts.map +1 -1
  200. package/dist/shared/sanitizer.js +28 -0
  201. package/dist/shared/sanitizer.js.map +1 -1
  202. package/dist/shared/sanitizer.test.js +20 -1
  203. package/dist/shared/sanitizer.test.js.map +1 -1
  204. package/dist/shared/webhook-fixtures.d.ts +33 -4
  205. package/dist/shared/webhook-fixtures.d.ts.map +1 -1
  206. package/dist/shared/webhook-fixtures.js +63 -21
  207. package/dist/shared/webhook-fixtures.js.map +1 -1
  208. package/package.json +6 -5
package/README.md CHANGED
@@ -1,6 +1,6 @@
1
1
  # GG Checkout MCP Server
2
2
 
3
- > Complete Model Context Protocol server for managing the GG Checkout platform via AI agents — 142 tools across 18 domains.
3
+ > Complete Model Context Protocol server for managing the GG Checkout platform via AI agents — 189 tools across 19 domains.
4
4
 
5
5
  ## Overview
6
6
 
@@ -36,6 +36,14 @@ npm install -g ggcheckout-mcp
36
36
 
37
37
  ### Claude Code
38
38
 
39
+ > **Upgrading?** The snippet below is unpinned: `npx -y ggcheckout-mcp` picks up
40
+ > **every** new version on the next start — minor releases included, not just
41
+ > majors. 0.3.0 carries two breaking changes: `create_checkout` takes
42
+ > `productId` instead of `id`, and checkout reads (`list_checkouts`,
43
+ > `get_checkout`, `update_checkout`) return that pointer as `productId` instead
44
+ > of `id`. Read [CHANGELOG.md](./CHANGELOG.md) first, and pin
45
+ > `ggcheckout-mcp@0.2.4` if this is not the moment.
46
+
39
47
  ```json
40
48
  {
41
49
  "mcpServers": {
@@ -69,11 +77,22 @@ export GGCHECKOUT_API_KEY="ggck_live_your_key_here"
69
77
  export GGCHECKOUT_API_URL="https://your-staging.example.com"
70
78
  ```
71
79
 
80
+ ### Upload folder
81
+
82
+ `upload_members_area_file` reads files from the machine running this server, and only from the
83
+ folder named here. Without it the tool refuses every upload: what an agent reads (a page, a PDF) can
84
+ carry instructions, so the server never reads an arbitrary path. A file that is itself a symbolic
85
+ link is refused, and a path that leads outside the folder through a link is too.
86
+
87
+ ```bash
88
+ export GGCHECKOUT_UPLOAD_ROOT="/home/me/course-import"
89
+ ```
90
+
72
91
  ---
73
92
 
74
- ## Available Tools (142)
93
+ ## Available Tools (189)
75
94
 
76
- ### Products (16 tools)
95
+ ### Products (18 tools)
77
96
 
78
97
  #### `list_products`
79
98
 
@@ -106,23 +125,43 @@ Create a new product/delivery.
106
125
 
107
126
  #### `update_product`
108
127
 
109
- Update an existing product. Only provide fields you want to change.
128
+ Update an existing product. Only provide fields you want to change; everything else is kept.
110
129
 
111
130
  **Parameters:** `productId` + any fields from create_product (all optional)
112
131
 
132
+ On accounts whose product read does not carry the file or the stock lines, an edit of a product
133
+ that delivers only one of those is refused with an explanation: the API checks the request body
134
+ for a deliverable, and those two cannot be read back to be sent along. Pass `url` with the
135
+ change, or make it in the dashboard.
136
+
113
137
  **Example prompt:** "Update product abc123 price to R$79.90"
114
138
 
115
139
  #### `delete_product`
116
140
 
117
141
  **Example prompt:** "Delete product abc123"
118
142
 
119
- #### `upload_deliverable`
143
+ #### `upload_deliverable` / `attach_deliverable` / `delete_deliverable`
144
+
145
+ Attaching a file takes two tool calls and one upload you perform yourself — the bytes never pass
146
+ through this server:
120
147
 
121
- Upload a deliverable file to a product.
148
+ 1. `upload_deliverable` (`productId`, `fileName`, `fileType`, `fileSize`) returns
149
+ `{ uploadUrl, filePath }`.
150
+ 2. `PUT` the raw bytes to `uploadUrl` with **only** `Content-Type: <fileType>` set. Do not send
151
+ an `Authorization` header — the signature is already in the URL and an extra header breaks it.
152
+ The URL is valid for one hour; the file may be up to 250MB.
153
+ 3. `attach_deliverable` (`productId`, `filePath`, `fileName`, `fileType`, `fileSize`) confirms the
154
+ upload landed and links it to the product.
122
155
 
123
- **Parameters:** `productId`, `fileUrl`, `fileName`, `fileType` (optional)
156
+ `attach_deliverable` keeps any link (`url`) the product already has; when both exist, the file
157
+ is what the buyer receives.
124
158
 
125
- **Example prompt:** "Upload the ebook at https://files.example.com/ebook.pdf to product abc123"
159
+ `delete_deliverable` unlinks the file; pass `filePath` to delete the stored bytes as well. It is
160
+ refused when the file is the product's only deliverable, since the API will not save a product
161
+ with nothing to deliver: give it a `url` first. If the unlink works and the byte deletion does
162
+ not, the answer carries `fileDeleteError` and the product stays unlinked.
163
+
164
+ **Example prompt:** "Attach ebook.pdf (2MB, application/pdf) to product abc123"
126
165
 
127
166
  #### `list_upsells` / `create_upsell` / `delete_upsell` / `reorder_upsells`
128
167
 
@@ -139,6 +178,27 @@ Manage downsells for a product.
139
178
 
140
179
  **Example prompt:** "Add a downsell to product abc123 with a 50% discount headline"
141
180
 
181
+ #### `get_offer_snippets` / `set_offer_product_page` (offers on the seller's page)
182
+
183
+ The post-purchase funnel is one ordered sequence of products, and each product opens either on the
184
+ GG offer page or on the seller's own page ("Minha página"). Both can be mixed in the same funnel: the
185
+ funnel order decides where the buyer goes after accepting or declining, and each product opens on its
186
+ own kind of page.
187
+
188
+ - `set_offer_product_page` puts ONE product of an upsell or downsell on the seller's page (the page
189
+ where its buttons are pasted, the two texts and the button color), or back on the GG page with
190
+ `page: null` (the stored page is kept, so moving it back loses nothing).
191
+ - `get_offer_snippets` is read only: every product of the offer in funnel order, and for each one on
192
+ the seller's page the HTML to paste there (the same as "Copiar HTML" in the dashboard) and the page
193
+ it goes on. An agent with access to the seller's landing page can paste each snippet where the
194
+ buttons should appear, keeping the `<script>` tag.
195
+
196
+ Each snippet works only for its own product, when the funnel order reaches it. Pages must be https;
197
+ plain http only works for localhost against a development server.
198
+
199
+ **Example prompt:** "Put the second product of upsell u1 of product abc123 on https://seller.com/oferta
200
+ with a green button saying 'Quero!', then give me the HTML to paste on that page"
201
+
142
202
  #### `manage_tags`
143
203
 
144
204
  Set tags on a product. Tags have a name and a hex color.
@@ -157,17 +217,35 @@ Set tags on a product. Tags have a name and a hex color.
157
217
 
158
218
  **Example prompt:** "Get details of checkout abc123"
159
219
 
160
- > **Note:** Use the `uid` (Firestore document ID), not the custom `id` slug.
220
+ > **Note:** A checkout has two identifiers, and every response carries both. Its
221
+ > own is `uid` (Firestore document ID) — that is what `get_checkout`,
222
+ > `update_checkout`, `delete_checkout` and `manage_checkout_tags` take. The other
223
+ > is `productId`, a foreign key pointing at the product this checkout sells; the
224
+ > API names that field `id`, and the server renames it on the way in and out.
161
225
 
162
226
  #### `create_checkout`
163
227
 
164
- **Required:** `title`, `id` (slug), `price`, `paymentMethods`, `checkout` (config)
228
+ Creates an offer for a product that already exists.
229
+
230
+ **Required:** `title`, `productId`, `price`, `paymentMethods`, `checkout` (config)
231
+
232
+ `productId` must be the uid returned by `create_product` (or a `uid` from
233
+ `list_products`) — not a slug. A checkout created against a product that doesn't
234
+ exist is an orphan the dashboard cannot open, so this is validated before the
235
+ checkout is created.
236
+
237
+ `price` is in Reais (`99.90`) and is converted to the cents the API stores.
238
+ `orderBumps` takes product uids; each one is resolved and snapshotted into the
239
+ shape the checkout page reads, so a uid that does not exist fails the call
240
+ instead of silently vanishing from the page.
165
241
 
166
242
  **Example prompt:** "Create a checkout page for my React Course priced at R$99.90"
167
243
 
168
244
  #### `update_checkout`
169
245
 
170
- Auto-merges with current data — only provide fields you want to change.
246
+ Only provide the fields you want to change. The API keeps every field missing from
247
+ the body as stored, so the tool sends the checkout's identity (title, owner, product,
248
+ price) plus your changes and nothing else from the stored document.
171
249
 
172
250
  **Example prompt:** "Update checkout abc123 price to R$79.90 and unpublish it"
173
251
 
@@ -217,11 +295,30 @@ Manage physical order fulfillment.
217
295
 
218
296
  **Example prompts:**
219
297
  - "Show me all my webhooks"
220
- - "Create a webhook for payment.paid events at https://myapp.com/webhook"
221
- - "Update webhook abc123 to also listen for payment.refunded"
298
+ - "Create a webhook for pix.paid events at https://myapp.com/webhook"
299
+ - "Update webhook abc123 to also listen for card.paid"
222
300
  - "Delete webhook abc123"
223
- - "Send a test payment.paid event to webhook abc123"
224
- - "Test my webhook abc123 with a refunded event overriding the payment ID to pay_xyz"
301
+ - "Send a test pix.paid event to webhook abc123"
302
+ - "Test my webhook abc123 with an expired event overriding the payment ID to pay_xyz"
303
+
304
+ #### Event names
305
+
306
+ The API stores the event names you register **without checking them**, and delivery matches
307
+ them exactly — so a name outside this list is accepted, saved, and never fires, with no error
308
+ anywhere. These are the names that exist:
309
+
310
+ | Family | Events |
311
+ |---|---|
312
+ | PIX | `pix.paid`, `pix.generated`, `pix.expired`, `pix.failed` |
313
+ | Card | `card.paid`, `card.generated`, `card.expired`, `card.failed`, `card.pending` |
314
+ | Subscription | `subscription.canceled`, `subscription.past_due`, `subscription.renewed` |
315
+ | Quiz funnel | `quiz.completed`, `quiz.lead_captured` |
316
+ | Cart | `checkout.abandoned` |
317
+
318
+ There is **no refund or chargeback event**: nothing dispatches one. `pix.failed` and
319
+ `card.pending` can be registered but have no emitter today. Names of the form
320
+ `payment.*` are the platform's internal vocabulary between services, not seller webhooks —
321
+ registering one gets you silence.
225
322
 
226
323
  #### Webhook Event Payloads
227
324
 
@@ -231,35 +328,35 @@ All events share the same top-level shape. Key fields:
231
328
  |---|---|---|
232
329
  | `event` | string | Event type (see below) |
233
330
  | `payment.id` | string | Payment identifier |
234
- | `payment.status` | string | `pending`, `paid`, `refunded`, `expired`, `chargeback` |
235
- | `payment.method` | string | `pix`, `pix.paid`, `card`, `card.paid` |
331
+ | `payment.status` | string | `pending`, `paid`, `expired` |
332
+ | `payment.method` | string | `pix`, `credit_card` |
236
333
  | `payment.amount` | number | Amount in **cents** (e.g. `9900` = R$99,00) |
237
334
  | `payment.customer.name` | string | Buyer name |
238
335
  | `payment.customer.email` | string | Buyer email |
239
336
  | `payment.customer.document` | string | CPF |
240
337
  | `payment.customer.phone` | string | Phone (E.164, e.g. `5511999999999`) |
241
338
  | `payment.createdAt` | string | ISO 8601 |
242
- | `payment.paidAt` | string \| undefined | Present on `payment.paid`, `payment.refunded`, `payment.chargeback` |
243
- | `payment.refundedAt` | string \| undefined | Present on `payment.refunded` |
244
- | `payment.expiredAt` | string \| undefined | Present on `payment.expired` |
339
+ | `payment.paidAt` | string \| undefined | Present on `pix.paid` and `card.paid` |
340
+ | `payment.expiredAt` | string \| undefined | Present on `pix.expired` and `card.expired` |
245
341
  | `product.id` | string | Product identifier |
246
342
  | `product.title` | string | Product name |
247
343
 
248
- **Supported events:**
344
+ **What `test_webhook` sends.** These bodies are built by the MCP server and posted straight to
345
+ your endpoint — the platform is not involved — so they are a plausible payment-shaped payload to
346
+ exercise your handler with, not a byte-for-byte copy of a live delivery:
249
347
 
250
348
  ```json
251
- { "event": "payment.created", "payment": { "status": "pending", "method": "pix" }, ... }
252
- { "event": "payment.paid", "payment": { "status": "paid", "method": "pix.paid", "paidAt": "..." }, ... }
253
- { "event": "payment.refunded", "payment": { "status": "refunded", "method": "pix.paid", "paidAt": "...", "refundedAt": "..." }, ... }
254
- { "event": "payment.expired", "payment": { "status": "expired", "method": "pix", "expiredAt": "..." }, ... }
255
- { "event": "payment.chargeback", "payment": { "status": "chargeback", "method": "card.paid", "paidAt": "..." }, ... }
349
+ { "event": "pix.paid", "payment": { "status": "paid", "method": "pix", "paidAt": "..." }, ... }
350
+ { "event": "card.paid", "payment": { "status": "paid", "method": "credit_card", "paidAt": "..." }, ... }
351
+ { "event": "pix.expired", "payment": { "status": "expired", "method": "pix", "expiredAt": "..." }, ... }
352
+ { "event": "card.expired", "payment": { "status": "expired", "method": "credit_card", "expiredAt": "..." }, ... }
256
353
  ```
257
354
 
258
355
  **Signature verification** (when a `secret` is set):
259
356
 
260
357
  ```
261
358
  X-Webhook-Signature: sha256=<HMAC-SHA256(secret, raw_body)>
262
- X-GGCheckout-Event: payment.paid
359
+ X-GGCheckout-Event: pix.paid
263
360
  ```
264
361
 
265
362
  ```ts
@@ -270,32 +367,64 @@ const isValid = sig === incomingHeader.replace('sha256=', '');
270
367
 
271
368
  ---
272
369
 
273
- ### Store (9 tools)
370
+ ### Store (28 tools)
371
+
372
+ `list_stores` returns your stores' ids; every other store tool takes one.
373
+
374
+ **Manage the store:** `create_store`, `get_store`, `update_store`, `delete_store`;
375
+ categories with `list_store_categories`, `create_store_category`, `update_store_category`,
376
+ `delete_store_category`; review moderation with `list_store_reviews`, `create_store_review`,
377
+ `update_store_review`, `delete_store_review`. `update_store` merges objects into the stored
378
+ config and replaces lists (`productOrder`, gateways, a category's `productIds`). Creating or
379
+ publishing a store requires a seller with verified email and phone.
380
+
381
+ **Store builder:** `get_store_layout`, `update_store_layout`, `publish_store_layout`,
382
+ `list_store_layout_history`, `restore_store_layout_version`, `get_store_theme`.
383
+ `update_store_layout` saves a draft and merges `theme`, `config` and `pageSettings` into the
384
+ stored ones; `blocks` replaces the whole list. Nothing is public until you publish.
385
+
386
+ **Catalog reads** (`get_store_public`, `list_store_products`, `get_store_product`,
387
+ `list_categories`, `list_feedbacks`) read the public storefront: they only see published
388
+ stores, list approved reviews only, and may be cached for up to 7 days.
389
+ `get_store_order` only returns pending orders with an API key.
390
+
391
+ Store integrations, store upsells/downsells, video, sales notifications and custom fields
392
+ are dashboard-only.
274
393
 
275
394
  **Example prompts:**
276
- - "Show me my store configuration"
395
+ - "Create a store called 'Loja Teste', turn on PIX with my AmploPay gateway and publish it"
396
+ - "Create a 'Cursos' category with products abc and def"
397
+ - "Approve all pending reviews of my store"
398
+ - "List my stores"
399
+ - "Change the primary color of my store to #8b5cf6 and publish it"
400
+ - "Undo the last store publish"
277
401
  - "List all products in my store"
278
- - "Get product details for product abc123 in store xyz"
279
- - "Show me the categories in my store"
280
402
  - "List customer reviews for my store with rating stats"
281
403
  - "Validate coupon code SAVE20 for an order of R$100"
282
404
 
283
405
  ---
284
406
 
285
- ### Funnels / Quiz (9 tools)
407
+ ### Funnels / Quiz (10 tools)
408
+
409
+ A quiz is a funnel: `question` components with options and scores, `result` components,
410
+ `scoring.ranges` and conditional `flow.edges`. `update_funnel` merges `design` and `settings`
411
+ into the stored ones; `steps`, `flow` and `scoring` replace the stored value, so read the
412
+ funnel first and send the full array back. Pixels and webhooks are linked by id
413
+ (`settings.pixelTokenIds` from `list_tokens`, `settings.webhookIds` from `list_webhooks`).
414
+ `list_funnel_checkouts` gives the checkouts and gateways a `pix` component can use.
286
415
 
287
416
  **Example prompts:**
288
417
  - "List all my funnels"
289
- - "Show me the details of funnel abc123"
290
- - "Create a new funnel called 'Lead Capture'"
418
+ - "Create a quiz with 3 questions that scores leads into beginner and advanced"
419
+ - "Change the primary color of funnel abc123 to red"
420
+ - "Send the leads of funnel abc123 to my Zapier webhook"
291
421
  - "Duplicate funnel abc123"
292
422
  - "Show me the leads from funnel abc123 that completed all steps"
293
- - "What's the conversion rate for funnel abc123?"
294
423
  - "Show me the drop-off analytics for each step in funnel abc123"
295
424
 
296
425
  ---
297
426
 
298
- ### Members Area (21 tools)
427
+ ### Members Area (32 tools)
299
428
 
300
429
  **Example prompts:**
301
430
  - "List all my members areas"
@@ -308,6 +437,23 @@ const isValid = sig === incomingHeader.replace('sha256=', '');
308
437
  - "Import these 50 students to members area xyz"
309
438
  - "Block student abc123"
310
439
 
440
+ **Files the seller sends.** `upload_members_area_file` uploads a file that is already on the machine
441
+ running this server (an absolute path inside `GGCHECKOUT_UPLOAD_ROOT`, see "Upload folder") and
442
+ returns the URL to pass on:
443
+
444
+ | `kind` | Accepts | Use the `url` in |
445
+ |---|---|---|
446
+ | `image` | jpg, png, webp, gif, avif | `update_members_area` branding (logo, banner), module `imageUrl`, section and lesson `thumbnailUrl` |
447
+ | `video` | mp4, webm, mov, avi, mpeg — up to 500 MB | `create_lesson` type `video`: `videoUrl` and `content: { videoUrl, videoSourceType: "upload" }` |
448
+ | `file` | pdf, doc(x), xls(x), zip, rar, 7z, mp3, ogg, wav, images, videos — up to 100 MB; needs `areaId` | `create_pdf_lessons`, `create_lesson` `content.fileUrl`, or `add_lesson_attachment` |
449
+
450
+ Nothing is downloaded from another platform: videos and PDFs come from the seller. Modules and
451
+ sections take `dripSettings` (release N days after purchase, enrollment or first access); lessons
452
+ take a cover and a position. `update_module` / `update_section` / `update_lesson` change only the
453
+ fields sent, and `delete_module` / `delete_section` / `delete_lesson` remove the item with everything
454
+ under it — irreversible, so they take `confirm: true`. These six need the API release with the
455
+ `PATCH`/`DELETE` structure routes; an older deployment answers that it has no such route yet.
456
+
311
457
  ---
312
458
 
313
459
  ### Discounts / Coupons (6 tools)
@@ -321,7 +467,7 @@ const isValid = sig === incomingHeader.replace('sha256=', '');
321
467
 
322
468
  ---
323
469
 
324
- ### WhatsApp (15 tools)
470
+ ### WhatsApp (13 tools)
325
471
 
326
472
  **Example prompts:**
327
473
  - "List my WhatsApp sessions"
@@ -336,7 +482,7 @@ const isValid = sig === incomingHeader.replace('sha256=', '');
336
482
 
337
483
  ---
338
484
 
339
- ### Billing (10 tools)
485
+ ### Billing (11 tools)
340
486
 
341
487
  **Example prompts:**
342
488
  - "What's my current billing balance?"
@@ -359,14 +505,16 @@ const isValid = sig === incomingHeader.replace('sha256=', '');
359
505
 
360
506
  ---
361
507
 
362
- ### Gateway Tokens (3 tools)
508
+ ### Gateway Tokens (4 tools)
363
509
 
364
510
  **Example prompts:**
365
511
  - "List my payment gateway tokens"
366
- - "Add a Stripe token"
512
+ - "Add a PushinPay token"
367
513
  - "Remove token abc123"
368
514
 
369
- Supports 26+ gateways: pushinpay, mercadopago, stripe, efibank, amplopay, infinitepay, abacatepay, and more.
515
+ `insert_token` creates only the four types the API accepts: `pushinpay`, `utmify`,
516
+ `emailprovider` and `mercadopago`. The platform processes payments through 25+ gateways, but the
517
+ others are connected from the dashboard, not through this API — asking for one here is refused.
370
518
 
371
519
  ---
372
520
 
@@ -400,13 +548,16 @@ Supports 26+ gateways: pushinpay, mercadopago, stripe, efibank, amplopay, infini
400
548
 
401
549
  ---
402
550
 
403
- ### Rewards / Goals (3 tools)
551
+ ### Rewards / Goals (2 tools)
404
552
 
405
553
  **Example prompts:**
406
554
  - "What's my progress on sales milestones?"
407
- - "Recalculate my reward progress"
408
555
  - "Redeem the 10K bracelet reward"
409
556
 
557
+ `calculate_rewards` is the only reader: it returns the progress and the milestone list together,
558
+ in reais (`currentRevenueCents` carries the same value in cents). There is no reward catalogue
559
+ endpoint, and a cache miss is rate limited to 10 per hour.
560
+
410
561
  ---
411
562
 
412
563
  ### Profile / Auth (6 tools)
@@ -428,6 +579,20 @@ Supports 26+ gateways: pushinpay, mercadopago, stripe, efibank, amplopay, infini
428
579
 
429
580
  ---
430
581
 
582
+ ### Telegram (15 tools)
583
+
584
+ Bots (`list_telegram_bots`, `get_telegram_bot`, `create_telegram_bot`, `update_telegram_bot`,
585
+ `delete_telegram_bot`, `validate_telegram_token`, `get_telegram_bot_groups`), flows
586
+ (`list_telegram_flows`, `get_telegram_flow`, `create_telegram_flow`, `update_telegram_flow`,
587
+ `delete_telegram_flow`, `deploy_telegram_flow`), `list_telegram_leads` and `telegram_media_upload`.
588
+
589
+ **Example prompts:**
590
+ - "List my Telegram bots"
591
+ - "Create a basic flow for bot abc123 and deploy it"
592
+ - "Show the qualified leads of bot abc123"
593
+
594
+ ---
595
+
431
596
  ## Price Formats
432
597
 
433
598
  Prices are accepted in two formats:
@@ -513,7 +678,7 @@ for each item:
513
678
  ## Local Development
514
679
 
515
680
  ```bash
516
- git clone https://github.com/gui-drumond/ggcheckout-mcp.git
681
+ git clone https://github.com/ggCheckout/ggcheckout-mcp.git
517
682
  cd ggcheckout-mcp
518
683
  npm install
519
684
  ```
@@ -523,6 +688,7 @@ npm install
523
688
  ```bash
524
689
  GGCHECKOUT_API_KEY=ggck_live_your_key_here
525
690
  GGCHECKOUT_API_URL=http://localhost:3000 # optional, defaults to https://ggcheckout.app
691
+ GGCHECKOUT_UPLOAD_ROOT=/path/to/import # needed by upload_members_area_file, the only folder it reads from
526
692
  ```
527
693
 
528
694
  ### Commands
@@ -561,7 +727,11 @@ Opens a browser UI to test any tool interactively.
561
727
  ### Error: 404 Not Found
562
728
 
563
729
  - The resource ID doesn't exist
564
- - For checkouts, use the `uid` (Firestore document ID), not the custom `id` slug
730
+ - For checkouts, use the `uid` (Firestore document ID) returned by `list_checkouts`
731
+ - Note that `create_checkout` takes a different identifier: `productId`, the uid
732
+ of the product being sold
733
+ - `Product <id> not found` from `create_checkout` means the product is missing or
734
+ belongs to another seller — the API answers 403 for both, so they look alike
565
735
 
566
736
  ### Error: 429 Too Many Requests
567
737
 
@@ -579,9 +749,9 @@ Opens a browser UI to test any tool interactively.
579
749
 
580
750
  ## Support
581
751
 
582
- - 📧 Email: support@ggcheckout.com
752
+ - 📧 Email: suporte@ggcheckout.com
583
753
  - 📖 Docs: https://docs.ggcheckout.com
584
- - 🐛 Issues: https://github.com/gui-drumond/ggcheckout-mcp/issues
754
+ - 🐛 Issues: https://github.com/ggCheckout/ggcheckout-mcp/issues
585
755
 
586
756
  ## License
587
757
 
@@ -46,7 +46,7 @@ export const adapters = {
46
46
  export const services = {
47
47
  product: new ProductService(adapters.product),
48
48
  payment: new PaymentService(adapters.payment, authAdapter),
49
- checkout: new CheckoutService(adapters.checkout, authAdapter),
49
+ checkout: new CheckoutService(adapters.checkout, authAdapter, adapters.product),
50
50
  webhook: new WebhookService(adapters.webhook, authAdapter),
51
51
  store: new StoreService(adapters.store),
52
52
  funnel: new FunnelService(adapters.funnel),
@@ -1 +1 @@
1
- {"version":3,"file":"setup.js","sourceRoot":"","sources":["../../src/__e2e__/setup.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"setup.js","sourceRoot":"","sources":["../../src/__e2e__/setup.ts"],"names":[],"mappings":"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"}
@@ -1,4 +1,4 @@
1
1
  import type { McpServer } from '@modelcontextprotocol/sdk/server/mcp.js';
2
- import type { BillingService } from '../../../core/services/billing.service.js';
2
+ import { type BillingService } from '../../../core/services/billing.service.js';
3
3
  export declare function registerBillingTools(server: McpServer, service: BillingService): void;
4
4
  //# sourceMappingURL=billing.tools.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"billing.tools.d.ts","sourceRoot":"","sources":["../../../../src/adapters/inbound/tools/billing.tools.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,yCAAyC,CAAC;AACzE,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,2CAA2C,CAAC;AAGhF,wBAAgB,oBAAoB,CAAC,MAAM,EAAE,SAAS,EAAE,OAAO,EAAE,cAAc,QAkE9E"}
1
+ {"version":3,"file":"billing.tools.d.ts","sourceRoot":"","sources":["../../../../src/adapters/inbound/tools/billing.tools.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,yCAAyC,CAAC;AACzE,OAAO,EAGL,KAAK,cAAc,EACpB,MAAM,2CAA2C,CAAC;AAGnD,wBAAgB,oBAAoB,CAAC,MAAM,EAAE,SAAS,EAAE,OAAO,EAAE,cAAc,QAiG9E"}
@@ -1,4 +1,5 @@
1
1
  import { z } from 'zod';
2
+ import { MAX_TOPUP_CENTS, MIN_TOPUP_CENTS, } from '../../../core/services/billing.service.js';
2
3
  import { createToolHandler } from '../tool-handler.js';
3
4
  export function registerBillingTools(server, service) {
4
5
  server.tool('get_billing_balance', 'Get current billing balance, credit, usage %, and next charge date', createToolHandler('get_billing_balance', async () => service.getBalance()));
@@ -32,18 +33,43 @@ export function registerBillingTools(server, service) {
32
33
  },
33
34
  }, createToolHandler('pay_invoice', async ({ invoiceId, method }) => service.payInvoice(invoiceId, method)));
34
35
  server.registerTool('list_credits', {
35
- description: 'List billing credits',
36
+ description: 'The credit statement. Returns `credits` (legacy PIX credits, with `status`) and `ledger` '
37
+ + '({ entries, nextBefore }), which is the statement for an account on the new billing. One of '
38
+ + 'the two is empty depending on the account, and that is the true answer, not an error: read '
39
+ + 'whichever has rows. Ledger `amountCents` is signed (credit +, debit −) and `balanceAfterCents` '
40
+ + 'is the running balance. Page the ledger by passing `before` = the `nextBefore` you got. If one '
41
+ + 'side could not be read, its list is empty and `creditsError` / `ledgerError` says why.',
36
42
  inputSchema: {
37
- status: z.enum(['pending', 'confirmed', 'used', 'expired']).optional().describe('Filter by credit status'),
38
- limit: z.number().min(1).max(1000).optional().describe('Max credits to return (default: 20)'),
43
+ status: z.enum(['pending', 'confirmed', 'used', 'expired']).optional()
44
+ .describe('Filter the legacy credits by status (does not apply to the ledger)'),
45
+ limit: z.number().int().min(1).max(200).optional()
46
+ .describe('Max rows (legacy default 20, ledger default 50; 200 is the lowest cap of the two routes)'),
47
+ before: z.string().optional()
48
+ .describe('Ledger cursor: the `nextBefore` from the previous page (RFC3339)'),
39
49
  },
40
50
  }, createToolHandler('list_credits', async (args) => service.listCredits(args)));
41
51
  server.registerTool('add_credit', {
42
- description: 'Add billing credit via PIX. Returns QR code for payment.',
52
+ description: 'Add billing credit via PIX. Returns { creditId, amountCents, pixCode, pixQrBase64, expiresAt, via }: '
53
+ + '`pixCode` is the copy-and-paste string and `pixQrBase64` the QR image (base64, no `data:` prefix). '
54
+ + 'Works on both billing generations — the right route is picked for the account, and `via` says '
55
+ + 'which one answered. The credit only exists once the PIX is actually paid. On a timeout, a 502 '
56
+ + 'or a 504 the PIX may have been opened anyway: check get_credit_topup (new billing) or the pending '
57
+ + 'entries of list_credits (legacy) before calling this again.',
43
58
  inputSchema: {
44
- amountCents: z.number().min(0).describe('Credit amount in cents'),
59
+ amountCents: z.number()
60
+ .int('amountCents is a whole number of CENTS: R$ 10,00 is 1000')
61
+ .min(MIN_TOPUP_CENTS, `amountCents is at least ${MIN_TOPUP_CENTS} CENTS (R$ 3,25)`)
62
+ .max(MAX_TOPUP_CENTS, `amountCents is at most ${MAX_TOPUP_CENTS} CENTS (R$ 250,00)`)
63
+ .describe(`Credit amount in CENTS, ${MIN_TOPUP_CENTS} to ${MAX_TOPUP_CENTS} (R$ 3,25 to R$ 250,00). R$ 10,00 is 1000`),
64
+ idempotencyKey: z.string().min(1).max(128).optional()
65
+ .describe('A stable key that makes a retry reuse the same top-up instead of opening another. Only '
66
+ + 'the new billing reads it (without one it dedupes by amount within 2 minutes); the legacy '
67
+ + 'billing ignores it and reuses the PIX already opened for the same amount, for 30 minutes.'),
45
68
  },
46
- }, createToolHandler('add_credit', async ({ amountCents }) => service.addCredit(amountCents)));
69
+ }, createToolHandler('add_credit', async ({ amountCents, idempotencyKey }) => service.addCredit(amountCents, idempotencyKey)));
70
+ server.tool('get_credit_topup', 'The current credit top-up on the new billing: { creditId, amountCents, status (pending, paid, '
71
+ + 'expired), pixCode, pixQrBase64, expiresAt }, or null when there is none. A pending top-up is not '
72
+ + 'in the list_credits ledger until it is paid, so this is where to find one opened by add_credit.', createToolHandler('get_credit_topup', async () => ({ topup: await service.getCreditTopup() })));
47
73
  server.tool('get_card_status', 'Get saved card status (validated, brand, last four, expiring soon)', createToolHandler('get_card_status', async () => service.getCardStatus()));
48
74
  server.tool('remove_card', 'Remove the saved billing card', createToolHandler('remove_card', async () => {
49
75
  await service.removeCard();
@@ -1 +1 @@
1
- {"version":3,"file":"billing.tools.js","sourceRoot":"","sources":["../../../../src/adapters/inbound/tools/billing.tools.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"billing.tools.js","sourceRoot":"","sources":["../../../../src/adapters/inbound/tools/billing.tools.ts"],"names":[],"mappings":"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"}
@@ -1 +1 @@
1
- {"version":3,"file":"checkout.tools.d.ts","sourceRoot":"","sources":["../../../../src/adapters/inbound/tools/checkout.tools.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,yCAAyC,CAAC;AACzE,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,4CAA4C,CAAC;AAoDlF,wBAAgB,qBAAqB,CAAC,MAAM,EAAE,SAAS,EAAE,OAAO,EAAE,eAAe,QAoHhF"}
1
+ {"version":3,"file":"checkout.tools.d.ts","sourceRoot":"","sources":["../../../../src/adapters/inbound/tools/checkout.tools.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,yCAAyC,CAAC;AACzE,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,4CAA4C,CAAC;AAoDlF,wBAAgB,qBAAqB,CAAC,MAAM,EAAE,SAAS,EAAE,OAAO,EAAE,eAAe,QA6HhF"}
@@ -58,18 +58,20 @@ export function registerCheckoutTools(server, service) {
58
58
  return { checkout };
59
59
  }));
60
60
  server.registerTool('create_checkout', {
61
- description: 'Create a new checkout page',
61
+ description: 'Create a new checkout page (an offer for an existing product)',
62
62
  inputSchema: {
63
63
  title: z.string().max(200).describe('Checkout page title'),
64
- id: z.string().max(100).describe('Unique checkout ID (slug)'),
65
- price: z.number().min(0).describe('Price in Brazilian Reais (e.g., 99.90)'),
64
+ productId: z.string().min(1).max(100).regex(/^[A-Za-z0-9_-]+$/, 'productId must be a product uid').describe('Uid of the product this checkout sells — the `productId` returned by create_product, '
65
+ + 'or a `uid` from list_products. NOT a slug and NOT a name you invent: an invented '
66
+ + 'value creates an orphan checkout the seller cannot open in the dashboard.'),
67
+ price: z.number().min(0).describe('Price in Brazilian Reais (e.g., 99.90) — converted to cents before it is sent'),
66
68
  paymentMethods: paymentMethodsSchema.describe('Payment methods configuration (credit_card, pix, bank_slip)'),
67
69
  checkout: z.record(z.string(), z.unknown()).describe('Checkout page styling/configuration'),
68
70
  url: z.string().url().optional().describe('Checkout URL (optional)'),
69
71
  bannerUrl: z.string().url().optional().describe('Banner image URL (optional)'),
70
72
  image: z.string().url().optional().describe('Product image URL (optional)'),
71
73
  sellerName: z.string().max(200).optional().describe('Seller name (optional)'),
72
- orderBumps: z.array(z.string()).max(20).optional().describe('Order bump product IDs (optional)'),
74
+ orderBumps: z.array(z.string()).max(20).optional().describe('Uids of products offered as order bumps, resolved and snapshotted server-side (optional)'),
73
75
  fields: fieldsSchema.optional().describe('Custom form fields config (havePhone, haveName, haveCpf)'),
74
76
  socialCard: socialCardSchema.optional().describe('Social proof cards (optional)'),
75
77
  published: z.boolean().optional().describe('Published status (default: true)'),
@@ -85,14 +87,19 @@ export function registerCheckoutTools(server, service) {
85
87
  inputSchema: {
86
88
  checkoutId: z.string().describe('Checkout ID (uid)'),
87
89
  title: z.string().max(200).optional().describe('Checkout page title'),
88
- price: z.number().min(0).optional().describe('Price in Brazilian Reais'),
90
+ price: z.number().min(0).optional().describe('Price in Brazilian Reais — converted to cents before it is sent'),
89
91
  paymentMethods: paymentMethodsSchema.optional().describe('Payment methods configuration'),
90
- checkout: z.record(z.string(), z.unknown()).optional().describe('Checkout page styling/configuration'),
91
- url: z.string().url().optional().describe('Checkout URL'),
92
+ checkout: z.record(z.string(), z.unknown()).optional()
93
+ .describe('Checkout page configuration, merged into the stored one (send only the keys to change). '
94
+ + 'Payment methods are changed through `paymentMethods`; the stored ones are never re-sent from here'),
95
+ url: z.string().url().optional()
96
+ .describe('Where the buyer goes after the post-purchase funnel (upsells and downsells), or right after the '
97
+ + "purchase when there is none. The offers on the seller's own page are set per product with "
98
+ + 'set_offer_product_page, not here'),
92
99
  bannerUrl: z.string().url().optional().describe('Banner image URL'),
93
100
  image: z.string().url().optional().describe('Product image URL'),
94
101
  sellerName: z.string().max(200).optional().describe('Seller name'),
95
- orderBumps: z.array(z.string()).max(20).optional().describe('Order bump product IDs'),
102
+ orderBumps: z.array(z.string()).max(20).optional().describe('Uids of products offered as order bumps, resolved and snapshotted server-side'),
96
103
  fields: fieldsSchema.optional().describe('Custom form fields config'),
97
104
  socialCard: socialCardSchema.optional().describe('Social proof cards'),
98
105
  published: z.boolean().optional().describe('Published status'),