@vendure/mcp-plugin 3.8.0-minor-bootstrap.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 (389) hide show
  1. package/lib/api/api-extensions.d.ts +2 -0
  2. package/lib/api/api-extensions.js +239 -0
  3. package/lib/api/api-extensions.js.map +1 -0
  4. package/lib/api/mcp-actor.service.d.ts +19 -0
  5. package/lib/api/mcp-actor.service.js +52 -0
  6. package/lib/api/mcp-actor.service.js.map +1 -0
  7. package/lib/api/mcp-admin.resolver.d.ts +105 -0
  8. package/lib/api/mcp-admin.resolver.js +463 -0
  9. package/lib/api/mcp-admin.resolver.js.map +1 -0
  10. package/lib/api/mcp-shop.resolver.d.ts +25 -0
  11. package/lib/api/mcp-shop.resolver.js +74 -0
  12. package/lib/api/mcp-shop.resolver.js.map +1 -0
  13. package/lib/check-options.d.ts +7 -0
  14. package/lib/check-options.js +130 -0
  15. package/lib/check-options.js.map +1 -0
  16. package/lib/constants.d.ts +48 -0
  17. package/lib/constants.js +72 -0
  18. package/lib/constants.js.map +1 -0
  19. package/lib/delete-in-batches.d.ts +5 -0
  20. package/lib/delete-in-batches.js +28 -0
  21. package/lib/delete-in-batches.js.map +1 -0
  22. package/lib/entities/index.d.ts +5 -0
  23. package/lib/entities/index.js +22 -0
  24. package/lib/entities/index.js.map +1 -0
  25. package/lib/entities/mcp-authorization-code.entity.d.ts +33 -0
  26. package/lib/entities/mcp-authorization-code.entity.js +77 -0
  27. package/lib/entities/mcp-authorization-code.entity.js.map +1 -0
  28. package/lib/entities/mcp-authorization-request.entity.d.ts +31 -0
  29. package/lib/entities/mcp-authorization-request.entity.js +73 -0
  30. package/lib/entities/mcp-authorization-request.entity.js.map +1 -0
  31. package/lib/entities/mcp-oauth-client.entity.d.ts +56 -0
  32. package/lib/entities/mcp-oauth-client.entity.js +70 -0
  33. package/lib/entities/mcp-oauth-client.entity.js.map +1 -0
  34. package/lib/entities/mcp-oauth-grant.entity.d.ts +77 -0
  35. package/lib/entities/mcp-oauth-grant.entity.js +121 -0
  36. package/lib/entities/mcp-oauth-grant.entity.js.map +1 -0
  37. package/lib/entities/mcp-tool-call-log.entity.d.ts +50 -0
  38. package/lib/entities/mcp-tool-call-log.entity.js +101 -0
  39. package/lib/entities/mcp-tool-call-log.entity.js.map +1 -0
  40. package/lib/events/mcp-tool-call.event.d.ts +17 -0
  41. package/lib/events/mcp-tool-call.event.js +23 -0
  42. package/lib/events/mcp-tool-call.event.js.map +1 -0
  43. package/lib/get-client-ip.d.ts +2 -0
  44. package/lib/get-client-ip.js +10 -0
  45. package/lib/get-client-ip.js.map +1 -0
  46. package/lib/get-language-code.d.ts +3 -0
  47. package/lib/get-language-code.js +12 -0
  48. package/lib/get-language-code.js.map +1 -0
  49. package/lib/index.d.ts +6 -0
  50. package/lib/index.js +26 -0
  51. package/lib/index.js.map +1 -0
  52. package/lib/internal-types.d.ts +27 -0
  53. package/lib/internal-types.js +3 -0
  54. package/lib/internal-types.js.map +1 -0
  55. package/lib/logging/mcp-tool-call-log-retention.service.d.ts +8 -0
  56. package/lib/logging/mcp-tool-call-log-retention.service.js +54 -0
  57. package/lib/logging/mcp-tool-call-log-retention.service.js.map +1 -0
  58. package/lib/logging/mcp-tool-call-log.service.d.ts +24 -0
  59. package/lib/logging/mcp-tool-call-log.service.js +128 -0
  60. package/lib/logging/mcp-tool-call-log.service.js.map +1 -0
  61. package/lib/oauth/cimd/cimd-client-resolver.service.d.ts +18 -0
  62. package/lib/oauth/cimd/cimd-client-resolver.service.js +109 -0
  63. package/lib/oauth/cimd/cimd-client-resolver.service.js.map +1 -0
  64. package/lib/oauth/cimd/cimd-document.d.ts +11 -0
  65. package/lib/oauth/cimd/cimd-document.js +66 -0
  66. package/lib/oauth/cimd/cimd-document.js.map +1 -0
  67. package/lib/oauth/cimd/cimd-fetch.d.ts +14 -0
  68. package/lib/oauth/cimd/cimd-fetch.js +192 -0
  69. package/lib/oauth/cimd/cimd-fetch.js.map +1 -0
  70. package/lib/oauth/cimd/cimd-url.d.ts +5 -0
  71. package/lib/oauth/cimd/cimd-url.js +94 -0
  72. package/lib/oauth/cimd/cimd-url.js.map +1 -0
  73. package/lib/oauth/grant-session.service.d.ts +19 -0
  74. package/lib/oauth/grant-session.service.js +141 -0
  75. package/lib/oauth/grant-session.service.js.map +1 -0
  76. package/lib/oauth/oauth-error.d.ts +18 -0
  77. package/lib/oauth/oauth-error.js +60 -0
  78. package/lib/oauth/oauth-error.js.map +1 -0
  79. package/lib/oauth/oauth-metadata.service.d.ts +34 -0
  80. package/lib/oauth/oauth-metadata.service.js +107 -0
  81. package/lib/oauth/oauth-metadata.service.js.map +1 -0
  82. package/lib/oauth/oauth-retention.service.d.ts +23 -0
  83. package/lib/oauth/oauth-retention.service.js +103 -0
  84. package/lib/oauth/oauth-retention.service.js.map +1 -0
  85. package/lib/oauth/oauth-types.d.ts +61 -0
  86. package/lib/oauth/oauth-types.js +32 -0
  87. package/lib/oauth/oauth-types.js.map +1 -0
  88. package/lib/oauth/oauth-utils.d.ts +20 -0
  89. package/lib/oauth/oauth-utils.js +111 -0
  90. package/lib/oauth/oauth-utils.js.map +1 -0
  91. package/lib/oauth/oauth.controller.d.ts +31 -0
  92. package/lib/oauth/oauth.controller.js +132 -0
  93. package/lib/oauth/oauth.controller.js.map +1 -0
  94. package/lib/oauth/oauth.service.d.ts +69 -0
  95. package/lib/oauth/oauth.service.js +650 -0
  96. package/lib/oauth/oauth.service.js.map +1 -0
  97. package/lib/oauth/token-hash.d.ts +6 -0
  98. package/lib/oauth/token-hash.js +21 -0
  99. package/lib/oauth/token-hash.js.map +1 -0
  100. package/lib/plugin.d.ts +54 -0
  101. package/lib/plugin.js +171 -0
  102. package/lib/plugin.js.map +1 -0
  103. package/lib/rate-limit/ip-bucket-key.d.ts +1 -0
  104. package/lib/rate-limit/ip-bucket-key.js +35 -0
  105. package/lib/rate-limit/ip-bucket-key.js.map +1 -0
  106. package/lib/rate-limit/mcp-oauth-rate-limit.guard.d.ts +20 -0
  107. package/lib/rate-limit/mcp-oauth-rate-limit.guard.js +63 -0
  108. package/lib/rate-limit/mcp-oauth-rate-limit.guard.js.map +1 -0
  109. package/lib/rate-limit/mcp-rate-limiter.service.d.ts +47 -0
  110. package/lib/rate-limit/mcp-rate-limiter.service.js +248 -0
  111. package/lib/rate-limit/mcp-rate-limiter.service.js.map +1 -0
  112. package/lib/registry/bm25.d.ts +12 -0
  113. package/lib/registry/bm25.js +60 -0
  114. package/lib/registry/bm25.js.map +1 -0
  115. package/lib/registry/mcp-tool-execution.service.d.ts +45 -0
  116. package/lib/registry/mcp-tool-execution.service.js +72 -0
  117. package/lib/registry/mcp-tool-execution.service.js.map +1 -0
  118. package/lib/registry/mcp-tool-registry.service.d.ts +89 -0
  119. package/lib/registry/mcp-tool-registry.service.js +668 -0
  120. package/lib/registry/mcp-tool-registry.service.js.map +1 -0
  121. package/lib/registry/mcp-tool-schema.service.d.ts +42 -0
  122. package/lib/registry/mcp-tool-schema.service.js +229 -0
  123. package/lib/registry/mcp-tool-schema.service.js.map +1 -0
  124. package/lib/registry/registry-types.d.ts +32 -0
  125. package/lib/registry/registry-types.js +3 -0
  126. package/lib/registry/registry-types.js.map +1 -0
  127. package/lib/resolve-options.d.ts +7 -0
  128. package/lib/resolve-options.js +85 -0
  129. package/lib/resolve-options.js.map +1 -0
  130. package/lib/shared/endpoint-paths.d.ts +8 -0
  131. package/lib/shared/endpoint-paths.js +12 -0
  132. package/lib/shared/endpoint-paths.js.map +1 -0
  133. package/lib/shared/loopback.d.ts +2 -0
  134. package/lib/shared/loopback.js +9 -0
  135. package/lib/shared/loopback.js.map +1 -0
  136. package/lib/shop-session/mcp-shop-session.service.d.ts +47 -0
  137. package/lib/shop-session/mcp-shop-session.service.js +132 -0
  138. package/lib/shop-session/mcp-shop-session.service.js.map +1 -0
  139. package/lib/tasks/mcp-oauth-retention.task.d.ts +9 -0
  140. package/lib/tasks/mcp-oauth-retention.task.js +21 -0
  141. package/lib/tasks/mcp-oauth-retention.task.js.map +1 -0
  142. package/lib/tasks/mcp-tool-call-log-retention.task.d.ts +7 -0
  143. package/lib/tasks/mcp-tool-call-log-retention.task.js +22 -0
  144. package/lib/tasks/mcp-tool-call-log-retention.task.js.map +1 -0
  145. package/lib/tools/built-in/active-order.service.d.ts +26 -0
  146. package/lib/tools/built-in/active-order.service.js +125 -0
  147. package/lib/tools/built-in/active-order.service.js.map +1 -0
  148. package/lib/tools/built-in/admin/add-customer-to-group.tool.d.ts +23 -0
  149. package/lib/tools/built-in/admin/add-customer-to-group.tool.js +68 -0
  150. package/lib/tools/built-in/admin/add-customer-to-group.tool.js.map +1 -0
  151. package/lib/tools/built-in/admin/add-note-to-order.tool.d.ts +104 -0
  152. package/lib/tools/built-in/admin/add-note-to-order.tool.js +66 -0
  153. package/lib/tools/built-in/admin/add-note-to-order.tool.js.map +1 -0
  154. package/lib/tools/built-in/admin/adjust-stock.tool.d.ts +26 -0
  155. package/lib/tools/built-in/admin/adjust-stock.tool.js +88 -0
  156. package/lib/tools/built-in/admin/adjust-stock.tool.js.map +1 -0
  157. package/lib/tools/built-in/admin/cancel-order.tool.d.ts +17 -0
  158. package/lib/tools/built-in/admin/cancel-order.tool.js +60 -0
  159. package/lib/tools/built-in/admin/cancel-order.tool.js.map +1 -0
  160. package/lib/tools/built-in/admin/channel-access.d.ts +2 -0
  161. package/lib/tools/built-in/admin/channel-access.js +9 -0
  162. package/lib/tools/built-in/admin/channel-access.js.map +1 -0
  163. package/lib/tools/built-in/admin/create-customer.tool.d.ts +41 -0
  164. package/lib/tools/built-in/admin/create-customer.tool.js +57 -0
  165. package/lib/tools/built-in/admin/create-customer.tool.js.map +1 -0
  166. package/lib/tools/built-in/admin/create-fulfillment.tool.d.ts +118 -0
  167. package/lib/tools/built-in/admin/create-fulfillment.tool.js +156 -0
  168. package/lib/tools/built-in/admin/create-fulfillment.tool.js.map +1 -0
  169. package/lib/tools/built-in/admin/create-product.tool.d.ts +52 -0
  170. package/lib/tools/built-in/admin/create-product.tool.js +61 -0
  171. package/lib/tools/built-in/admin/create-product.tool.js.map +1 -0
  172. package/lib/tools/built-in/admin/create-variant.tool.d.ts +48 -0
  173. package/lib/tools/built-in/admin/create-variant.tool.js +79 -0
  174. package/lib/tools/built-in/admin/create-variant.tool.js.map +1 -0
  175. package/lib/tools/built-in/admin/entity-field-schemas.d.ts +36 -0
  176. package/lib/tools/built-in/admin/entity-field-schemas.js +63 -0
  177. package/lib/tools/built-in/admin/entity-field-schemas.js.map +1 -0
  178. package/lib/tools/built-in/admin/get-customer.tool.d.ts +28 -0
  179. package/lib/tools/built-in/admin/get-customer.tool.js +55 -0
  180. package/lib/tools/built-in/admin/get-customer.tool.js.map +1 -0
  181. package/lib/tools/built-in/admin/get-order.tool.d.ts +100 -0
  182. package/lib/tools/built-in/admin/get-order.tool.js +68 -0
  183. package/lib/tools/built-in/admin/get-order.tool.js.map +1 -0
  184. package/lib/tools/built-in/admin/get-product.tool.d.ts +69 -0
  185. package/lib/tools/built-in/admin/get-product.tool.js +77 -0
  186. package/lib/tools/built-in/admin/get-product.tool.js.map +1 -0
  187. package/lib/tools/built-in/admin/get-stock-levels.tool.d.ts +23 -0
  188. package/lib/tools/built-in/admin/get-stock-levels.tool.js +61 -0
  189. package/lib/tools/built-in/admin/get-stock-levels.tool.js.map +1 -0
  190. package/lib/tools/built-in/admin/index.d.ts +25 -0
  191. package/lib/tools/built-in/admin/index.js +54 -0
  192. package/lib/tools/built-in/admin/index.js.map +1 -0
  193. package/lib/tools/built-in/admin/list-channels.tool.d.ts +24 -0
  194. package/lib/tools/built-in/admin/list-channels.tool.js +56 -0
  195. package/lib/tools/built-in/admin/list-channels.tool.js.map +1 -0
  196. package/lib/tools/built-in/admin/list-customer-groups.tool.d.ts +23 -0
  197. package/lib/tools/built-in/admin/list-customer-groups.tool.js +52 -0
  198. package/lib/tools/built-in/admin/list-customer-groups.tool.js.map +1 -0
  199. package/lib/tools/built-in/admin/list-customers.tool.d.ts +62 -0
  200. package/lib/tools/built-in/admin/list-customers.tool.js +66 -0
  201. package/lib/tools/built-in/admin/list-customers.tool.js.map +1 -0
  202. package/lib/tools/built-in/admin/list-orders.tool.d.ts +142 -0
  203. package/lib/tools/built-in/admin/list-orders.tool.js +87 -0
  204. package/lib/tools/built-in/admin/list-orders.tool.js.map +1 -0
  205. package/lib/tools/built-in/admin/list-products.tool.d.ts +63 -0
  206. package/lib/tools/built-in/admin/list-products.tool.js +71 -0
  207. package/lib/tools/built-in/admin/list-products.tool.js.map +1 -0
  208. package/lib/tools/built-in/admin/refund-order.tool.d.ts +38 -0
  209. package/lib/tools/built-in/admin/refund-order.tool.js +115 -0
  210. package/lib/tools/built-in/admin/refund-order.tool.js.map +1 -0
  211. package/lib/tools/built-in/admin/set-active-channel.tool.d.ts +22 -0
  212. package/lib/tools/built-in/admin/set-active-channel.tool.js +84 -0
  213. package/lib/tools/built-in/admin/set-active-channel.tool.js.map +1 -0
  214. package/lib/tools/built-in/admin/translation-schemas.d.ts +12 -0
  215. package/lib/tools/built-in/admin/translation-schemas.js +17 -0
  216. package/lib/tools/built-in/admin/translation-schemas.js.map +1 -0
  217. package/lib/tools/built-in/admin/update-customer.tool.d.ts +42 -0
  218. package/lib/tools/built-in/admin/update-customer.tool.js +59 -0
  219. package/lib/tools/built-in/admin/update-customer.tool.js.map +1 -0
  220. package/lib/tools/built-in/admin/update-order-state.tool.d.ts +16 -0
  221. package/lib/tools/built-in/admin/update-order-state.tool.js +58 -0
  222. package/lib/tools/built-in/admin/update-order-state.tool.js.map +1 -0
  223. package/lib/tools/built-in/admin/update-product.tool.d.ts +53 -0
  224. package/lib/tools/built-in/admin/update-product.tool.js +68 -0
  225. package/lib/tools/built-in/admin/update-product.tool.js.map +1 -0
  226. package/lib/tools/built-in/admin/update-variant.tool.d.ts +46 -0
  227. package/lib/tools/built-in/admin/update-variant.tool.js +77 -0
  228. package/lib/tools/built-in/admin/update-variant.tool.js.map +1 -0
  229. package/lib/tools/built-in/admin/upload-asset.tool.d.ts +32 -0
  230. package/lib/tools/built-in/admin/upload-asset.tool.js +56 -0
  231. package/lib/tools/built-in/admin/upload-asset.tool.js.map +1 -0
  232. package/lib/tools/built-in/catalog-query.service.d.ts +21 -0
  233. package/lib/tools/built-in/catalog-query.service.js +128 -0
  234. package/lib/tools/built-in/catalog-query.service.js.map +1 -0
  235. package/lib/tools/built-in/custom-field-input.service.d.ts +10 -0
  236. package/lib/tools/built-in/custom-field-input.service.js +64 -0
  237. package/lib/tools/built-in/custom-field-input.service.js.map +1 -0
  238. package/lib/tools/built-in/email-schema.d.ts +2 -0
  239. package/lib/tools/built-in/email-schema.js +12 -0
  240. package/lib/tools/built-in/email-schema.js.map +1 -0
  241. package/lib/tools/built-in/id-schema.d.ts +3 -0
  242. package/lib/tools/built-in/id-schema.js +11 -0
  243. package/lib/tools/built-in/id-schema.js.map +1 -0
  244. package/lib/tools/built-in/int32-schema.d.ts +4 -0
  245. package/lib/tools/built-in/int32-schema.js +8 -0
  246. package/lib/tools/built-in/int32-schema.js.map +1 -0
  247. package/lib/tools/built-in/list-helpers.d.ts +48 -0
  248. package/lib/tools/built-in/list-helpers.js +76 -0
  249. package/lib/tools/built-in/list-helpers.js.map +1 -0
  250. package/lib/tools/built-in/order-list-helpers.d.ts +20 -0
  251. package/lib/tools/built-in/order-list-helpers.js +48 -0
  252. package/lib/tools/built-in/order-list-helpers.js.map +1 -0
  253. package/lib/tools/built-in/providers.d.ts +2 -0
  254. package/lib/tools/built-in/providers.js +7 -0
  255. package/lib/tools/built-in/providers.js.map +1 -0
  256. package/lib/tools/built-in/remote-asset.d.ts +4 -0
  257. package/lib/tools/built-in/remote-asset.js +54 -0
  258. package/lib/tools/built-in/remote-asset.js.map +1 -0
  259. package/lib/tools/built-in/serializer.service.d.ts +327 -0
  260. package/lib/tools/built-in/serializer.service.js +413 -0
  261. package/lib/tools/built-in/serializer.service.js.map +1 -0
  262. package/lib/tools/built-in/shop/add-to-cart.tool.d.ts +21 -0
  263. package/lib/tools/built-in/shop/add-to-cart.tool.js +100 -0
  264. package/lib/tools/built-in/shop/add-to-cart.tool.js.map +1 -0
  265. package/lib/tools/built-in/shop/address-schema.d.ts +15 -0
  266. package/lib/tools/built-in/shop/address-schema.js +20 -0
  267. package/lib/tools/built-in/shop/address-schema.js.map +1 -0
  268. package/lib/tools/built-in/shop/apply-coupon-code.tool.d.ts +17 -0
  269. package/lib/tools/built-in/shop/apply-coupon-code.tool.js +62 -0
  270. package/lib/tools/built-in/shop/apply-coupon-code.tool.js.map +1 -0
  271. package/lib/tools/built-in/shop/collection-lookup.d.ts +15 -0
  272. package/lib/tools/built-in/shop/collection-lookup.js +35 -0
  273. package/lib/tools/built-in/shop/collection-lookup.js.map +1 -0
  274. package/lib/tools/built-in/shop/get-cart.tool.d.ts +94 -0
  275. package/lib/tools/built-in/shop/get-cart.tool.js +55 -0
  276. package/lib/tools/built-in/shop/get-cart.tool.js.map +1 -0
  277. package/lib/tools/built-in/shop/get-collection.tool.d.ts +42 -0
  278. package/lib/tools/built-in/shop/get-collection.tool.js +64 -0
  279. package/lib/tools/built-in/shop/get-collection.tool.js.map +1 -0
  280. package/lib/tools/built-in/shop/get-eligible-payment-methods.tool.d.ts +26 -0
  281. package/lib/tools/built-in/shop/get-eligible-payment-methods.tool.js +58 -0
  282. package/lib/tools/built-in/shop/get-eligible-payment-methods.tool.js.map +1 -0
  283. package/lib/tools/built-in/shop/get-eligible-shipping-methods.tool.d.ts +30 -0
  284. package/lib/tools/built-in/shop/get-eligible-shipping-methods.tool.js +59 -0
  285. package/lib/tools/built-in/shop/get-eligible-shipping-methods.tool.js.map +1 -0
  286. package/lib/tools/built-in/shop/get-my-account.tool.d.ts +22 -0
  287. package/lib/tools/built-in/shop/get-my-account.tool.js +57 -0
  288. package/lib/tools/built-in/shop/get-my-account.tool.js.map +1 -0
  289. package/lib/tools/built-in/shop/get-order.tool.d.ts +100 -0
  290. package/lib/tools/built-in/shop/get-order.tool.js +67 -0
  291. package/lib/tools/built-in/shop/get-order.tool.js.map +1 -0
  292. package/lib/tools/built-in/shop/get-product.tool.d.ts +57 -0
  293. package/lib/tools/built-in/shop/get-product.tool.js +81 -0
  294. package/lib/tools/built-in/shop/get-product.tool.js.map +1 -0
  295. package/lib/tools/built-in/shop/index.d.ts +19 -0
  296. package/lib/tools/built-in/shop/index.js +42 -0
  297. package/lib/tools/built-in/shop/index.js.map +1 -0
  298. package/lib/tools/built-in/shop/list-collections.tool.d.ts +42 -0
  299. package/lib/tools/built-in/shop/list-collections.tool.js +75 -0
  300. package/lib/tools/built-in/shop/list-collections.tool.js.map +1 -0
  301. package/lib/tools/built-in/shop/list-my-orders.tool.d.ts +100 -0
  302. package/lib/tools/built-in/shop/list-my-orders.tool.js +63 -0
  303. package/lib/tools/built-in/shop/list-my-orders.tool.js.map +1 -0
  304. package/lib/tools/built-in/shop/place-order.tool.d.ts +188 -0
  305. package/lib/tools/built-in/shop/place-order.tool.js +152 -0
  306. package/lib/tools/built-in/shop/place-order.tool.js.map +1 -0
  307. package/lib/tools/built-in/shop/product-search-query.d.ts +4 -0
  308. package/lib/tools/built-in/shop/product-search-query.js +34 -0
  309. package/lib/tools/built-in/shop/product-search-query.js.map +1 -0
  310. package/lib/tools/built-in/shop/remove-coupon-code.tool.d.ts +17 -0
  311. package/lib/tools/built-in/shop/remove-coupon-code.tool.js +63 -0
  312. package/lib/tools/built-in/shop/remove-coupon-code.tool.js.map +1 -0
  313. package/lib/tools/built-in/shop/remove-from-cart.tool.d.ts +17 -0
  314. package/lib/tools/built-in/shop/remove-from-cart.tool.js +58 -0
  315. package/lib/tools/built-in/shop/remove-from-cart.tool.js.map +1 -0
  316. package/lib/tools/built-in/shop/search-products.tool.d.ts +48 -0
  317. package/lib/tools/built-in/shop/search-products.tool.js +95 -0
  318. package/lib/tools/built-in/shop/search-products.tool.js.map +1 -0
  319. package/lib/tools/built-in/shop/set-checkout-details.tool.d.ts +56 -0
  320. package/lib/tools/built-in/shop/set-checkout-details.tool.js +187 -0
  321. package/lib/tools/built-in/shop/set-checkout-details.tool.js.map +1 -0
  322. package/lib/tools/built-in/shop/set-shipping-method.tool.d.ts +17 -0
  323. package/lib/tools/built-in/shop/set-shipping-method.tool.js +58 -0
  324. package/lib/tools/built-in/shop/set-shipping-method.tool.js.map +1 -0
  325. package/lib/tools/built-in/shop/update-cart-line.tool.d.ts +18 -0
  326. package/lib/tools/built-in/shop/update-cart-line.tool.js +60 -0
  327. package/lib/tools/built-in/shop/update-cart-line.tool.js.map +1 -0
  328. package/lib/tools/built-in/string-schemas.d.ts +4 -0
  329. package/lib/tools/built-in/string-schemas.js +13 -0
  330. package/lib/tools/built-in/string-schemas.js.map +1 -0
  331. package/lib/transport/mcp-server.factory.d.ts +13 -0
  332. package/lib/transport/mcp-server.factory.js +32 -0
  333. package/lib/transport/mcp-server.factory.js.map +1 -0
  334. package/lib/transport/mcp-transport.controller.d.ts +77 -0
  335. package/lib/transport/mcp-transport.controller.js +442 -0
  336. package/lib/transport/mcp-transport.controller.js.map +1 -0
  337. package/lib/types.d.ts +432 -0
  338. package/lib/types.js +3 -0
  339. package/lib/types.js.map +1 -0
  340. package/package.json +42 -0
  341. package/src/dashboard/components/activity-block.tsx +72 -0
  342. package/src/dashboard/components/actor-cell.tsx +31 -0
  343. package/src/dashboard/components/connection-dialog.tsx +106 -0
  344. package/src/dashboard/components/empty-cell.tsx +7 -0
  345. package/src/dashboard/components/grants-block.tsx +218 -0
  346. package/src/dashboard/components/stats-block.tsx +275 -0
  347. package/src/dashboard/components/tools-block.tsx +274 -0
  348. package/src/dashboard/components/tooltip-button.tsx +28 -0
  349. package/src/dashboard/components/use-mcp-table-state.ts +47 -0
  350. package/src/dashboard/i18n/ar.po +311 -0
  351. package/src/dashboard/i18n/bg.po +311 -0
  352. package/src/dashboard/i18n/cs.po +311 -0
  353. package/src/dashboard/i18n/de.po +311 -0
  354. package/src/dashboard/i18n/en.po +311 -0
  355. package/src/dashboard/i18n/es.po +311 -0
  356. package/src/dashboard/i18n/fa.po +311 -0
  357. package/src/dashboard/i18n/fr.po +311 -0
  358. package/src/dashboard/i18n/he.po +311 -0
  359. package/src/dashboard/i18n/hr.po +311 -0
  360. package/src/dashboard/i18n/hu.po +311 -0
  361. package/src/dashboard/i18n/it.po +311 -0
  362. package/src/dashboard/i18n/ja.po +311 -0
  363. package/src/dashboard/i18n/ko.po +311 -0
  364. package/src/dashboard/i18n/nb.po +311 -0
  365. package/src/dashboard/i18n/ne.po +311 -0
  366. package/src/dashboard/i18n/nl.po +311 -0
  367. package/src/dashboard/i18n/pl.po +311 -0
  368. package/src/dashboard/i18n/pt_BR.po +311 -0
  369. package/src/dashboard/i18n/pt_PT.po +311 -0
  370. package/src/dashboard/i18n/ro.po +311 -0
  371. package/src/dashboard/i18n/ru.po +311 -0
  372. package/src/dashboard/i18n/sv.po +311 -0
  373. package/src/dashboard/i18n/tr.po +311 -0
  374. package/src/dashboard/i18n/uk.po +311 -0
  375. package/src/dashboard/i18n/uz.po +311 -0
  376. package/src/dashboard/i18n/zh_Hans.po +311 -0
  377. package/src/dashboard/i18n/zh_Hant.po +311 -0
  378. package/src/dashboard/index.tsx +30 -0
  379. package/src/dashboard/mcp-activity-route.tsx +38 -0
  380. package/src/dashboard/mcp-authorize-route.tsx +369 -0
  381. package/src/dashboard/mcp-grants-route.tsx +38 -0
  382. package/src/dashboard/mcp-overview-route.tsx +46 -0
  383. package/src/dashboard/mcp-server-redirect-route.tsx +15 -0
  384. package/src/dashboard/mcp-tools-route.tsx +38 -0
  385. package/src/dashboard/mcp.graphql.ts +127 -0
  386. package/src/dashboard/published-files.spec.ts +54 -0
  387. package/src/dashboard/tsconfig.json +9 -0
  388. package/src/shared/endpoint-paths.ts +8 -0
  389. package/src/shared/loopback.ts +6 -0
@@ -0,0 +1,106 @@
1
+ import { Trans } from '@lingui/react/macro';
2
+ import {
3
+ api,
4
+ Button,
5
+ CopyableText,
6
+ Dialog,
7
+ DialogClose,
8
+ DialogContent,
9
+ DialogDescription,
10
+ DialogFooter,
11
+ DialogHeader,
12
+ DialogTitle,
13
+ DialogTrigger,
14
+ Separator,
15
+ useQuery,
16
+ } from '@vendure/dashboard';
17
+ import { ExternalLinkIcon, PlugIcon } from 'lucide-react';
18
+
19
+ import { mcpServerConfigQuery } from '../mcp.graphql';
20
+
21
+ const SETUP_GUIDE_URL = 'https://docs.vendure.io/guides/mcp-server/quick-start/';
22
+
23
+ function CopyableField({ label, value }: { label: React.ReactNode; value: string }) {
24
+ return (
25
+ <div className="space-y-1.5">
26
+ <div className="text-xs font-medium text-muted-foreground">{label}</div>
27
+ <CopyableText value={value} className="justify-between rounded-md border bg-muted/50 px-3 py-2">
28
+ <code className="min-w-0 flex-1 truncate font-mono text-xs select-all" title={value}>
29
+ {value}
30
+ </code>
31
+ </CopyableText>
32
+ </div>
33
+ );
34
+ }
35
+
36
+ // Behind a header button rather than on the page, so it doesn't compete with the day-to-day blocks.
37
+ export function ConnectionDialog() {
38
+ const { data, isLoading } = useQuery({
39
+ queryKey: ['mcp-server-config'],
40
+ queryFn: () => api.query(mcpServerConfigQuery),
41
+ });
42
+ const config = data?.mcpServerConfig;
43
+ // Clients reach the server on its OAuth issuer origin, which can differ from the dashboard's own origin.
44
+ const origin = config?.issuer ?? window.location.origin;
45
+ const adminUrl = `${origin}/mcp/admin`;
46
+ const shopUrl = `${origin}/mcp/shop`;
47
+ const inspectorCommand = 'npx @modelcontextprotocol/inspector';
48
+ // Until the config arrives both endpoints are shown, so the dialog does not flash empty.
49
+ const showAdminUrl = isLoading || config?.oauthConfigured !== false;
50
+ const showShopUrl = isLoading || config?.shopAccess !== 'disabled';
51
+
52
+ return (
53
+ <Dialog>
54
+ <DialogTrigger render={<Button variant="outline" />}>
55
+ <PlugIcon className="h-4 w-4" />
56
+ <Trans>Connect a client</Trans>
57
+ </DialogTrigger>
58
+ <DialogContent className="sm:max-w-lg">
59
+ <DialogHeader>
60
+ <DialogTitle>
61
+ <Trans>Connect a client</Trans>
62
+ </DialogTitle>
63
+ <DialogDescription>
64
+ <Trans>Connect an MCP client to your Vendure server using the endpoints below.</Trans>
65
+ </DialogDescription>
66
+ </DialogHeader>
67
+
68
+ <div className="space-y-4">
69
+ {showAdminUrl ? (
70
+ <CopyableField label={<Trans>Admin API</Trans>} value={adminUrl} />
71
+ ) : (
72
+ <p className="text-sm text-muted-foreground">
73
+ <Trans>
74
+ The admin endpoint needs OAuth. Add an oauth block to McpPlugin.init to enable
75
+ it.
76
+ </Trans>
77
+ </p>
78
+ )}
79
+ {showShopUrl ? (
80
+ <CopyableField label={<Trans>Shop API</Trans>} value={shopUrl} />
81
+ ) : (
82
+ <p className="text-sm text-muted-foreground">
83
+ <Trans>The shop endpoint is disabled (shopAccess: 'disabled').</Trans>
84
+ </p>
85
+ )}
86
+ <Separator />
87
+ <CopyableField label={<Trans>Test with MCP Inspector</Trans>} value={inspectorCommand} />
88
+ </div>
89
+
90
+ <DialogFooter className="sm:items-center sm:justify-between">
91
+ <Button
92
+ variant="link"
93
+ className="px-0"
94
+ render={<a href={SETUP_GUIDE_URL} target="_blank" rel="noreferrer noopener" />}
95
+ >
96
+ <ExternalLinkIcon className="h-3.5 w-3.5" />
97
+ <Trans>Setup guide for connecting MCP clients</Trans>
98
+ </Button>
99
+ <DialogClose render={<Button variant="outline" />}>
100
+ <Trans>Close</Trans>
101
+ </DialogClose>
102
+ </DialogFooter>
103
+ </DialogContent>
104
+ </Dialog>
105
+ );
106
+ }
@@ -0,0 +1,7 @@
1
+ /**
2
+ * Placeholder for a table cell that has no value, so every empty cell in the
3
+ * MCP tables looks the same.
4
+ */
5
+ export function EmptyCell() {
6
+ return <span className="text-muted-foreground">—</span>;
7
+ }
@@ -0,0 +1,218 @@
1
+ import { Trans, useLingui } from '@lingui/react/macro';
2
+ import {
3
+ Alert,
4
+ AlertDescription,
5
+ api,
6
+ Badge,
7
+ Button,
8
+ ConfirmationDialog,
9
+ DropdownMenu,
10
+ DropdownMenuContent,
11
+ DropdownMenuGroup,
12
+ DropdownMenuItem,
13
+ DropdownMenuTrigger,
14
+ PaginatedListDataTable,
15
+ type ResultOf,
16
+ toast,
17
+ useMutation,
18
+ usePermissions,
19
+ useQuery,
20
+ } from '@vendure/dashboard';
21
+ import { BanIcon, EllipsisIcon, InfoIcon } from 'lucide-react';
22
+ import { useRef } from 'react';
23
+
24
+ import { mcpOauthGrantsQuery, mcpServerConfigQuery, revokeMcpOauthGrantMutation } from '../mcp.graphql';
25
+
26
+ import { ActorCell } from './actor-cell';
27
+ import { EmptyCell } from './empty-cell';
28
+ import { useMcpTableState } from './use-mcp-table-state';
29
+
30
+ type Grant = ResultOf<typeof mcpOauthGrantsQuery>['mcpOauthGrants']['items'][number];
31
+
32
+ function GrantStatusBadge({ status }: { status: Grant['status'] }) {
33
+ if (status === 'revoked') {
34
+ return (
35
+ <Badge variant="destructive">
36
+ <Trans>Revoked</Trans>
37
+ </Badge>
38
+ );
39
+ }
40
+ if (status === 'expired') {
41
+ return (
42
+ <Badge variant="secondary">
43
+ <Trans>Expired</Trans>
44
+ </Badge>
45
+ );
46
+ }
47
+ return (
48
+ <Badge variant="default">
49
+ <Trans>Active</Trans>
50
+ </Badge>
51
+ );
52
+ }
53
+
54
+ export function GrantsBlock() {
55
+ const { t } = useLingui();
56
+ const { hasPermissions } = usePermissions();
57
+ const canUpdate = hasPermissions(['UpdateMcpServer']);
58
+ const tableState = useMcpTableState({
59
+ defaultSorting: [{ id: 'lastActivityAt', desc: true }],
60
+ defaultVisibility: {
61
+ id: false,
62
+ createdAt: false,
63
+ updatedAt: false,
64
+ actorId: false,
65
+ channelId: false,
66
+ revokedAt: false,
67
+ },
68
+ });
69
+ const refreshTable = useRef<() => void>(() => {
70
+ /* the table replaces this when it mounts */
71
+ });
72
+
73
+ const { data: configData } = useQuery({
74
+ queryKey: ['mcp-server-config'],
75
+ queryFn: () => api.query(mcpServerConfigQuery),
76
+ });
77
+ const oauthMissing = configData?.mcpServerConfig.oauthConfigured === false;
78
+
79
+ const revoke = useMutation({
80
+ mutationFn: (vars: { id: string }) => api.mutate(revokeMcpOauthGrantMutation, vars),
81
+ onSuccess: result => {
82
+ if (result.revokeMcpOauthGrant) {
83
+ toast.success(t`Grant revoked`);
84
+ } else {
85
+ toast.error(t`The grant could not be revoked; it may have already been removed`);
86
+ }
87
+ refreshTable.current();
88
+ },
89
+ onError: () => {
90
+ toast.error(t`Could not revoke grant`);
91
+ },
92
+ });
93
+
94
+ return (
95
+ <div className="space-y-4">
96
+ {oauthMissing ? (
97
+ <Alert>
98
+ <InfoIcon className="h-4 w-4" />
99
+ <AlertDescription>
100
+ <Trans>
101
+ OAuth is not configured, so no client can be granted access. Add an oauth block to
102
+ McpPlugin.init to use grants.
103
+ </Trans>
104
+ </AlertDescription>
105
+ </Alert>
106
+ ) : null}
107
+ <PaginatedListDataTable
108
+ listQuery={mcpOauthGrantsQuery}
109
+ registerRefresher={refresher => {
110
+ refreshTable.current = refresher;
111
+ }}
112
+ {...tableState}
113
+ includeSelectionColumn={false}
114
+ customizeColumns={{
115
+ oauthClientName: {
116
+ header: () => <Trans>Client</Trans>,
117
+ cell: ({ row }) =>
118
+ row.original.oauthClientName ? (
119
+ <span className="font-medium">{row.original.oauthClientName}</span>
120
+ ) : (
121
+ <EmptyCell />
122
+ ),
123
+ },
124
+ actorName: {
125
+ header: () => <Trans>Granted to</Trans>,
126
+ meta: { dependencies: ['actorType', 'customerId'] },
127
+ // No database column to sort or filter by; it's looked up per row.
128
+ enableSorting: false,
129
+ enableColumnFilter: false,
130
+ cell: ({ row }) => (
131
+ <ActorCell
132
+ actorType={row.original.actorType ?? null}
133
+ actorName={row.original.actorName ?? null}
134
+ customerId={row.original.customerId ?? null}
135
+ />
136
+ ),
137
+ },
138
+ actorType: {
139
+ header: () => <Trans>Actor type</Trans>,
140
+ cell: ({ row }) =>
141
+ row.original.actorType ? (
142
+ <Badge variant="outline">{row.original.actorType}</Badge>
143
+ ) : (
144
+ <EmptyCell />
145
+ ),
146
+ },
147
+ // Fetched only to feed the "Granted to" cell; no database column to sort or filter by.
148
+ customerId: { meta: { disabled: true } },
149
+ lastActivityAt: { header: () => <Trans>Last activity</Trans> },
150
+ expiresAt: { header: () => <Trans>Expires</Trans> },
151
+ status: {
152
+ header: () => <Trans>Status</Trans>,
153
+ cell: ({ row }) => <GrantStatusBadge status={row.original.status} />,
154
+ },
155
+ }}
156
+ additionalColumns={{
157
+ actions: {
158
+ header: () => <Trans>Actions</Trans>,
159
+ meta: { dependencies: ['id', 'revokedAt'] },
160
+ enableHiding: false,
161
+ // Shows a disabled control rather than nothing, so the row doesn't look broken.
162
+ cell: ({ row }) =>
163
+ row.original.revokedAt != null || !canUpdate ? (
164
+ <Button
165
+ variant="ghost"
166
+ size="icon"
167
+ disabled
168
+ aria-label={
169
+ row.original.revokedAt != null
170
+ ? t`No actions available for a revoked grant`
171
+ : t`Revoking needs the UpdateMcpServer permission`
172
+ }
173
+ >
174
+ <EllipsisIcon />
175
+ </Button>
176
+ ) : (
177
+ <DropdownMenu>
178
+ <DropdownMenuTrigger render={<Button variant="ghost" size="icon" />}>
179
+ <EllipsisIcon />
180
+ </DropdownMenuTrigger>
181
+ <DropdownMenuContent className="min-w-56">
182
+ <DropdownMenuGroup>
183
+ <ConfirmationDialog
184
+ title={t`Revoke grant`}
185
+ description={t`This immediately revokes the client's access. The client will need to authorize again to reconnect.`}
186
+ confirmText={t`Revoke`}
187
+ onConfirm={() => revoke.mutate({ id: row.original.id })}
188
+ >
189
+ <DropdownMenuItem closeOnClick={false}>
190
+ <div className="flex items-center gap-2">
191
+ <BanIcon className="w-4 h-4" />
192
+ <Trans>Revoke</Trans>
193
+ </div>
194
+ </DropdownMenuItem>
195
+ </ConfirmationDialog>
196
+ </DropdownMenuGroup>
197
+ </DropdownMenuContent>
198
+ </DropdownMenu>
199
+ ),
200
+ },
201
+ }}
202
+ // "actions" must stay last, so every other column is named here rather than left to append after it.
203
+ defaultColumnOrder={[
204
+ 'oauthClientName',
205
+ 'actorName',
206
+ 'actorType',
207
+ 'status',
208
+ 'lastActivityAt',
209
+ 'expiresAt',
210
+ 'actorId',
211
+ 'channelId',
212
+ 'revokedAt',
213
+ 'actions',
214
+ ]}
215
+ />
216
+ </div>
217
+ );
218
+ }
@@ -0,0 +1,275 @@
1
+ import { Trans, useLingui } from '@lingui/react/macro';
2
+ import {
3
+ Alert,
4
+ AlertDescription,
5
+ api,
6
+ Empty,
7
+ EmptyDescription,
8
+ EmptyHeader,
9
+ EmptyMedia,
10
+ EmptyTitle,
11
+ Link,
12
+ Progress,
13
+ Select,
14
+ SelectContent,
15
+ SelectItem,
16
+ SelectTrigger,
17
+ SelectValue,
18
+ Skeleton,
19
+ useQuery,
20
+ } from '@vendure/dashboard';
21
+ import {
22
+ ActivityIcon,
23
+ CircleCheckIcon,
24
+ CircleXIcon,
25
+ ClockIcon,
26
+ GaugeIcon,
27
+ InfoIcon,
28
+ TrendingUpIcon,
29
+ TriangleAlert,
30
+ } from 'lucide-react';
31
+ import { useState } from 'react';
32
+
33
+ import { mcpStatsQuery } from '../mcp.graphql';
34
+
35
+ import { TooltipButton } from './tooltip-button';
36
+
37
+ type TimeRange = '1h' | '24h' | '7d' | '30d';
38
+
39
+ function StatHint({ children }: { children: React.ReactNode }) {
40
+ const { t } = useLingui();
41
+ return (
42
+ <TooltipButton
43
+ tooltip={children}
44
+ label={t`What this number means`}
45
+ className="ml-1 inline-flex h-4 w-4 min-w-0 p-0 align-text-bottom text-muted-foreground"
46
+ >
47
+ <InfoIcon className="h-3 w-3" />
48
+ </TooltipButton>
49
+ );
50
+ }
51
+
52
+ function StatTile({
53
+ icon,
54
+ label,
55
+ value,
56
+ hint,
57
+ children,
58
+ }: {
59
+ icon: React.ReactNode;
60
+ label: React.ReactNode;
61
+ value: React.ReactNode;
62
+ hint?: React.ReactNode;
63
+ children?: React.ReactNode;
64
+ }) {
65
+ return (
66
+ <div className="rounded-md border border-border p-3 space-y-1">
67
+ <div className="flex items-start gap-1.5 text-xs text-muted-foreground">
68
+ <span className="mt-px shrink-0">{icon}</span>
69
+ <span>
70
+ {label}
71
+ {hint ? <StatHint>{hint}</StatHint> : null}
72
+ </span>
73
+ </div>
74
+ <div className="text-2xl font-semibold tabular-nums">{value}</div>
75
+ {children}
76
+ </div>
77
+ );
78
+ }
79
+
80
+ const regionsClasses = 'grid gap-4 @4xl:grid-cols-3';
81
+
82
+ const tilesClasses = '@4xl:col-span-2 grid grid-cols-2 @2xl:grid-cols-3 gap-3';
83
+
84
+ function StatsSkeleton() {
85
+ return (
86
+ <div className={regionsClasses}>
87
+ <div className={tilesClasses}>
88
+ {Array.from({ length: 6 }).map((_, index) => (
89
+ <Skeleton key={index} className="h-19 w-full" />
90
+ ))}
91
+ </div>
92
+ <div className="space-y-2">
93
+ <Skeleton className="h-5 w-24" />
94
+ <Skeleton className="h-6 w-full" />
95
+ </div>
96
+ </div>
97
+ );
98
+ }
99
+
100
+ function TopToolsList({ tools }: { tools: Array<{ toolName: string; count: number }> }) {
101
+ const topFive = tools.slice(0, 5);
102
+ const maxCount = Math.max(...topFive.map(tool => tool.count));
103
+ return (
104
+ <div className="space-y-2">
105
+ {topFive.map(tool => (
106
+ <div key={tool.toolName} className="space-y-1">
107
+ <div className="flex items-baseline justify-between gap-3">
108
+ <span className="font-mono text-sm truncate">{tool.toolName}</span>
109
+ <span className="text-sm tabular-nums text-muted-foreground">{tool.count}</span>
110
+ </div>
111
+ <div className="h-1 rounded-full bg-primary/20">
112
+ <div
113
+ className="h-1 rounded-full bg-primary"
114
+ style={{ width: `${(tool.count / maxCount) * 100}%` }}
115
+ />
116
+ </div>
117
+ </div>
118
+ ))}
119
+ </div>
120
+ );
121
+ }
122
+
123
+ function NoCallsRecorded() {
124
+ return (
125
+ <Empty className="border border-dashed p-6">
126
+ <EmptyHeader>
127
+ <EmptyMedia variant="icon">
128
+ <ActivityIcon />
129
+ </EmptyMedia>
130
+ <EmptyTitle>
131
+ <Trans>No tool calls yet</Trans>
132
+ </EmptyTitle>
133
+ <EmptyDescription>
134
+ <Trans>No calls recorded in this period.</Trans>
135
+ </EmptyDescription>
136
+ </EmptyHeader>
137
+ </Empty>
138
+ );
139
+ }
140
+
141
+ function formatLatency(ms: number | null): string {
142
+ return ms == null ? '—' : `${ms} ms`;
143
+ }
144
+
145
+ export function StatsBlock() {
146
+ const { t } = useLingui();
147
+ const [timeRange, setTimeRange] = useState<TimeRange>('24h');
148
+
149
+ const rangeLabels: Record<TimeRange, string> = {
150
+ '1h': t`Last hour`,
151
+ '24h': t`Last 24 hours`,
152
+ '7d': t`Last 7 days`,
153
+ '30d': t`Last 30 days`,
154
+ };
155
+
156
+ const { data, isLoading, error } = useQuery({
157
+ queryKey: ['mcp-stats', timeRange],
158
+ queryFn: () => api.query(mcpStatsQuery, { timeRange }),
159
+ });
160
+
161
+ const stats = data?.mcpStats;
162
+
163
+ if (error) {
164
+ return (
165
+ <Alert variant="destructive">
166
+ <TriangleAlert className="h-4 w-4" />
167
+ <AlertDescription>
168
+ <Trans>Error loading MCP statistics: {error.message}</Trans>
169
+ </AlertDescription>
170
+ </Alert>
171
+ );
172
+ }
173
+
174
+ const successRate = stats?.successRate ?? 0;
175
+ // The API reports the error rate, not a count, so the tile works the count back out.
176
+ const failedCalls = Math.round((stats?.totalCalls ?? 0) * (stats?.errorRate ?? 0));
177
+
178
+ return (
179
+ <div className="space-y-4">
180
+ <div className="flex items-center justify-between gap-2">
181
+ <div className="text-sm text-muted-foreground">
182
+ <Trans>Usage over the selected period</Trans>
183
+ </div>
184
+ <Select
185
+ items={rangeLabels}
186
+ value={timeRange}
187
+ onValueChange={value => {
188
+ if (value) setTimeRange(value);
189
+ }}
190
+ >
191
+ <SelectTrigger className="w-40">
192
+ <SelectValue />
193
+ </SelectTrigger>
194
+ <SelectContent>
195
+ {(Object.keys(rangeLabels) as TimeRange[]).map(key => (
196
+ <SelectItem key={key} value={key}>
197
+ {rangeLabels[key]}
198
+ </SelectItem>
199
+ ))}
200
+ </SelectContent>
201
+ </Select>
202
+ </div>
203
+
204
+ {isLoading && !stats ? (
205
+ <StatsSkeleton />
206
+ ) : (
207
+ <div className={regionsClasses}>
208
+ <div className={tilesClasses}>
209
+ <StatTile
210
+ icon={<ActivityIcon className="h-3.5 w-3.5" />}
211
+ label={<Trans>Total calls</Trans>}
212
+ value={stats?.totalCalls ?? 0}
213
+ />
214
+ <StatTile
215
+ icon={<CircleCheckIcon className="h-3.5 w-3.5" />}
216
+ label={<Trans>Success rate</Trans>}
217
+ value={`${(successRate * 100).toFixed(1)}%`}
218
+ >
219
+ <Progress className="pt-1" value={successRate * 100} />
220
+ </StatTile>
221
+ <StatTile
222
+ icon={<CircleXIcon className="h-3.5 w-3.5" />}
223
+ label={<Trans>Failed calls</Trans>}
224
+ value={failedCalls}
225
+ />
226
+ <StatTile
227
+ icon={<GaugeIcon className="h-3.5 w-3.5" />}
228
+ label={<Trans>p50 latency</Trans>}
229
+ value={formatLatency(stats?.p50LatencyMs ?? null)}
230
+ hint={<Trans>Half of the calls in this period finished faster than this.</Trans>}
231
+ />
232
+ <StatTile
233
+ icon={<ClockIcon className="h-3.5 w-3.5" />}
234
+ label={<Trans>p95 latency</Trans>}
235
+ value={formatLatency(stats?.p95LatencyMs ?? null)}
236
+ hint={
237
+ <Trans>
238
+ 95 out of 100 calls in this period finished faster than this. It shows how
239
+ slow the worst calls are.
240
+ </Trans>
241
+ }
242
+ />
243
+ <StatTile
244
+ icon={<TrendingUpIcon className="h-3.5 w-3.5" />}
245
+ label={<Trans>Calls per hour</Trans>}
246
+ value={(stats?.callsPerHour ?? 0).toFixed(1)}
247
+ hint={
248
+ <Trans>Average number of tool calls per hour over the selected period.</Trans>
249
+ }
250
+ />
251
+ </div>
252
+
253
+ <div className="space-y-2">
254
+ <div className="text-sm font-medium">
255
+ <Trans>Top tools</Trans>
256
+ </div>
257
+ {stats && stats.topTools.length > 0 ? (
258
+ <>
259
+ <TopToolsList tools={stats.topTools} />
260
+ <Link
261
+ to="/mcp-server/activity"
262
+ className="inline-block text-sm text-primary hover:underline"
263
+ >
264
+ <Trans>See all activity</Trans>
265
+ </Link>
266
+ </>
267
+ ) : (
268
+ <NoCallsRecorded />
269
+ )}
270
+ </div>
271
+ </div>
272
+ )}
273
+ </div>
274
+ );
275
+ }