@01.software/cli 0.9.0 → 0.10.1

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.
@@ -88,6 +88,382 @@ var MCP_CONSOLE_SERVICE_AUDIENCE = "https://api.01.software/internal/mcp";
88
88
  var MCP_CONSOLE_SERVICE_SCOPE = "console:mcp_proxy";
89
89
  var MCP_SERVICE_TOKEN_LIFETIME_SECONDS = 60;
90
90
 
91
+ // ../../packages/contracts/src/tenant/index.ts
92
+ import { z } from "zod";
93
+ var tenantFieldConfigStateSchema = z.object({
94
+ hiddenFields: z.array(z.string()),
95
+ isHidden: z.boolean()
96
+ }).strict();
97
+ var tenantContextQuerySchema = z.object({
98
+ counts: z.literal("true").optional()
99
+ }).strict();
100
+ var tenantContextToolInputSchema = z.object({
101
+ includeCounts: z.boolean().optional().default(false).describe(
102
+ "Include per-collection document counts and config status (bypasses cache, slower)"
103
+ )
104
+ }).strict();
105
+ var tenantContextResponseSchema = z.object({
106
+ tenant: z.object({
107
+ id: z.string(),
108
+ name: z.string(),
109
+ plan: z.string(),
110
+ planSource: z.string().optional(),
111
+ authoritative: z.boolean().optional(),
112
+ capabilityVersion: z.string().optional()
113
+ }).strict(),
114
+ features: z.array(z.string()),
115
+ collections: z.object({
116
+ active: z.array(z.string()),
117
+ inactive: z.array(z.string())
118
+ }).strict(),
119
+ fieldConfigs: z.record(z.string(), tenantFieldConfigStateSchema),
120
+ counts: z.record(z.string(), z.number()).optional(),
121
+ config: z.object({
122
+ webhookConfigured: z.boolean()
123
+ }).strict().optional()
124
+ }).strict();
125
+ var tenantFeatureProgressFeatureSchema = z.enum(["ecommerce"]);
126
+ var tenantFeatureProgressInputSchema = z.object({
127
+ feature: tenantFeatureProgressFeatureSchema.describe(
128
+ "Feature to inspect for tenant implementation readiness"
129
+ ),
130
+ includeEvidence: z.boolean().optional().default(false).describe("Include sanitized counts and static surface evidence")
131
+ }).strict();
132
+ var tenantFeatureProgressStatusSchema = z.enum([
133
+ "ready",
134
+ "attention",
135
+ "blocked"
136
+ ]);
137
+ var tenantFeatureProgressItemStateSchema = z.enum([
138
+ "complete",
139
+ "incomplete",
140
+ "blocked",
141
+ "attention",
142
+ "optional",
143
+ "unknown",
144
+ "manual",
145
+ "not-applicable"
146
+ ]);
147
+ var tenantFeatureProgressSeveritySchema = z.enum([
148
+ "required",
149
+ "recommended",
150
+ "optional"
151
+ ]);
152
+ var tenantFeatureProgressEvidenceValueSchema = z.union([
153
+ z.string(),
154
+ z.number(),
155
+ z.boolean(),
156
+ z.null()
157
+ ]);
158
+ var tenantFeatureProgressItemSchema = z.object({
159
+ id: z.string(),
160
+ title: z.string(),
161
+ state: tenantFeatureProgressItemStateSchema,
162
+ severity: tenantFeatureProgressSeveritySchema,
163
+ summary: z.string(),
164
+ evidence: z.record(z.string(), tenantFeatureProgressEvidenceValueSchema).optional()
165
+ }).strict();
166
+ var tenantFeatureProgressGroupSchema = z.object({
167
+ id: z.string(),
168
+ title: z.string(),
169
+ summary: z.string().optional(),
170
+ items: z.array(tenantFeatureProgressItemSchema)
171
+ }).strict();
172
+ var tenantFeatureProgressResponseSchema = z.object({
173
+ schemaVersion: z.literal(1),
174
+ feature: tenantFeatureProgressFeatureSchema,
175
+ status: tenantFeatureProgressStatusSchema,
176
+ generatedAt: z.string(),
177
+ tenant: z.object({
178
+ id: z.string(),
179
+ name: z.string(),
180
+ plan: z.string()
181
+ }).strict(),
182
+ capability: z.object({
183
+ effectiveFeatures: z.array(z.string()),
184
+ planBlocked: z.array(z.string()),
185
+ closureAdded: z.array(z.string())
186
+ }).strict(),
187
+ summary: z.object({
188
+ complete: z.number().int().nonnegative(),
189
+ total: z.number().int().nonnegative(),
190
+ blocking: z.number().int().nonnegative(),
191
+ manual: z.number().int().nonnegative(),
192
+ unknown: z.number().int().nonnegative()
193
+ }).strict(),
194
+ groups: z.array(tenantFeatureProgressGroupSchema)
195
+ }).strict();
196
+ var COLLECTION_SCHEMA_CONTRACT_VERSION = 1;
197
+ var collectionSchemaEndpointParamsSchema = z.object({
198
+ collectionSlug: z.string().min(1, "collectionSlug is required")
199
+ }).strict();
200
+ function createCollectionSchemaToolInputSchema(collections) {
201
+ return z.object({
202
+ collection: z.enum(collections).describe("Collection name (required)")
203
+ }).strict();
204
+ }
205
+ var collectionFieldOptionSchema = z.object({
206
+ label: z.string(),
207
+ value: z.string()
208
+ }).strict();
209
+ var collectionFieldSchema = z.lazy(
210
+ () => z.object({
211
+ name: z.string(),
212
+ path: z.string(),
213
+ type: z.string(),
214
+ required: z.literal(true).optional(),
215
+ unique: z.literal(true).optional(),
216
+ hasMany: z.literal(true).optional(),
217
+ relationTo: z.union([z.string(), z.array(z.string())]).optional(),
218
+ options: z.array(collectionFieldOptionSchema).optional(),
219
+ hidden: z.literal(true).optional(),
220
+ systemManaged: z.literal(true).optional(),
221
+ writable: z.boolean().optional(),
222
+ fields: z.array(collectionFieldSchema).optional()
223
+ }).strict()
224
+ );
225
+ var collectionSchemaResponseSchema = z.object({
226
+ contractVersion: z.literal(COLLECTION_SCHEMA_CONTRACT_VERSION),
227
+ mode: z.literal("effective"),
228
+ collection: z.object({
229
+ slug: z.string(),
230
+ timestamps: z.boolean(),
231
+ alwaysActive: z.boolean(),
232
+ feature: z.string().nullable(),
233
+ systemFields: z.array(z.string()),
234
+ visibility: z.object({
235
+ collectionHidden: z.boolean(),
236
+ hiddenFields: z.array(z.string())
237
+ }).strict(),
238
+ fields: z.array(collectionFieldSchema)
239
+ }).strict()
240
+ }).strict();
241
+
242
+ // ../../packages/contracts/src/ecommerce/index.ts
243
+ import { z as z2 } from "zod";
244
+ var transactionStatusSchema = z2.enum([
245
+ "pending",
246
+ "paid",
247
+ "failed",
248
+ "canceled"
249
+ ]);
250
+ var updateTransactionSchema = z2.object({
251
+ pgPaymentId: z2.string().min(1, "pgPaymentId is required").describe("PG payment ID (required)"),
252
+ status: transactionStatusSchema.describe(
253
+ "New transaction status (required)"
254
+ ),
255
+ paymentMethod: z2.string().optional().describe("Payment method (optional)"),
256
+ receiptUrl: z2.string().optional().describe("Receipt URL (optional)"),
257
+ paymentKey: z2.string().min(1).optional().describe("Provider payment key for verified paid confirmation"),
258
+ amount: z2.number().int().positive().optional().describe("Provider-confirmed amount for verified paid confirmation")
259
+ }).strict();
260
+ var UpdateTransactionSchema = updateTransactionSchema;
261
+ var providerSlugSchema = z2.string().trim().regex(/^[a-z0-9][a-z0-9_-]{0,63}$/, "pgProvider must be lowercase slug");
262
+ var confirmPaymentSchema = z2.object({
263
+ orderNumber: z2.string().min(1).optional(),
264
+ pgPaymentId: z2.string().min(1, "pgPaymentId is required").describe("Provider payment identifier stored on the transaction"),
265
+ pgProvider: providerSlugSchema.describe(
266
+ "Payment provider slug, e.g. toss, portone, stripe"
267
+ ),
268
+ pgOrderId: z2.string().min(1).optional(),
269
+ amount: z2.number().int().nonnegative("amount must be non-negative").describe("Provider-confirmed amount in minor units"),
270
+ currency: z2.string().min(1).optional(),
271
+ paymentMethod: z2.string().optional(),
272
+ receiptUrl: z2.string().url().optional(),
273
+ approvedAt: z2.string().optional(),
274
+ providerStatus: z2.string().optional(),
275
+ providerEventId: z2.string().min(1).optional(),
276
+ confirmationSource: z2.enum([
277
+ "provider_webhook",
278
+ "provider_lookup",
279
+ "provider_api_confirm",
280
+ "manual_server"
281
+ ]).optional(),
282
+ metadata: z2.record(z2.string(), z2.unknown()).optional()
283
+ }).strict();
284
+ var returnReasonSchema = z2.enum([
285
+ "change_of_mind",
286
+ "defective",
287
+ "wrong_delivery",
288
+ "damaged",
289
+ "other"
290
+ ]);
291
+ var restockActionSchema = z2.enum(["return_to_stock", "discard"]);
292
+ var returnWithRefundItemSchema = z2.object({
293
+ orderItem: z2.union([z2.string(), z2.number()]).transform(String),
294
+ quantity: z2.number().int().positive("quantity must be a positive integer"),
295
+ restockAction: restockActionSchema.default("return_to_stock")
296
+ }).strict();
297
+ var returnWithRefundSchema = z2.object({
298
+ orderNumber: z2.string().min(1, "orderNumber is required").describe("Order number (required)"),
299
+ reason: returnReasonSchema.optional().describe("Return reason (optional)"),
300
+ reasonDetail: z2.string().optional().describe("Detailed reason text (optional)"),
301
+ returnItems: z2.array(returnWithRefundItemSchema).min(1, "At least one return item is required").max(100, "Too many return items").describe("Array of products to return (required)"),
302
+ refundAmount: z2.number().min(0, "refundAmount must be non-negative").describe("Refund amount (required, min 0)"),
303
+ pgPaymentId: z2.string().min(1, "pgPaymentId is required").describe("PG payment ID for refund (required)"),
304
+ paymentKey: z2.string().min(1).optional().describe("Provider payment key for verified refund"),
305
+ refundReceiptUrl: z2.string().optional().describe("Refund receipt URL (optional)")
306
+ }).strict();
307
+ var ReturnWithRefundSchema = returnWithRefundSchema;
308
+
309
+ // ../../packages/contracts/src/mcp/index.ts
310
+ var MCP_TOOL_CONTRACT = {
311
+ "query-collection": {
312
+ consoleRole: "tenant-viewer",
313
+ oauthScope: "mcp:read",
314
+ readOnly: true
315
+ },
316
+ "get-collection-by-id": {
317
+ consoleRole: "tenant-viewer",
318
+ oauthScope: "mcp:read",
319
+ readOnly: true
320
+ },
321
+ "get-order": {
322
+ consoleRole: "tenant-viewer",
323
+ oauthScope: "mcp:read",
324
+ readOnly: true
325
+ },
326
+ "stock-check": {
327
+ consoleRole: "tenant-viewer",
328
+ oauthScope: "mcp:read",
329
+ readOnly: true
330
+ },
331
+ "validate-discount": {
332
+ consoleRole: "tenant-viewer",
333
+ oauthScope: "mcp:read",
334
+ readOnly: true
335
+ },
336
+ "calculate-shipping": {
337
+ consoleRole: "tenant-viewer",
338
+ oauthScope: "mcp:read",
339
+ readOnly: true
340
+ },
341
+ "get-collection-schema": {
342
+ consoleRole: "tenant-viewer",
343
+ oauthScope: "mcp:read",
344
+ readOnly: true
345
+ },
346
+ "list-configurable-fields": {
347
+ consoleRole: "tenant-viewer",
348
+ oauthScope: "mcp:read",
349
+ readOnly: true
350
+ },
351
+ "get-tenant-context": {
352
+ consoleRole: "tenant-viewer",
353
+ oauthScope: "mcp:read",
354
+ readOnly: true
355
+ },
356
+ "check-feature-progress": {
357
+ consoleRole: "tenant-viewer",
358
+ oauthScope: "mcp:read",
359
+ readOnly: true
360
+ },
361
+ "add-cart-item": {
362
+ consoleRole: "tenant-editor",
363
+ oauthScope: "mcp:write",
364
+ readOnly: false
365
+ },
366
+ "update-cart-item": {
367
+ consoleRole: "tenant-editor",
368
+ oauthScope: "mcp:write",
369
+ readOnly: false
370
+ },
371
+ "remove-cart-item": {
372
+ consoleRole: "tenant-editor",
373
+ oauthScope: "mcp:write",
374
+ readOnly: false
375
+ },
376
+ "clear-cart": {
377
+ consoleRole: "tenant-editor",
378
+ oauthScope: "mcp:write",
379
+ readOnly: false
380
+ },
381
+ "apply-discount": {
382
+ consoleRole: "tenant-editor",
383
+ oauthScope: "mcp:write",
384
+ readOnly: false
385
+ },
386
+ "remove-discount": {
387
+ consoleRole: "tenant-editor",
388
+ oauthScope: "mcp:write",
389
+ readOnly: false
390
+ },
391
+ checkout: {
392
+ consoleRole: "tenant-admin",
393
+ oauthScope: "mcp:write",
394
+ readOnly: false
395
+ },
396
+ "create-order": {
397
+ consoleRole: "tenant-admin",
398
+ oauthScope: "mcp:write",
399
+ readOnly: false
400
+ },
401
+ "update-order": {
402
+ consoleRole: "tenant-admin",
403
+ oauthScope: "mcp:write",
404
+ readOnly: false
405
+ },
406
+ "create-fulfillment": {
407
+ consoleRole: "tenant-admin",
408
+ oauthScope: "mcp:write",
409
+ readOnly: false
410
+ },
411
+ "update-fulfillment": {
412
+ consoleRole: "tenant-admin",
413
+ oauthScope: "mcp:write",
414
+ readOnly: false
415
+ },
416
+ "create-return": {
417
+ consoleRole: "tenant-admin",
418
+ oauthScope: "mcp:write",
419
+ readOnly: false
420
+ },
421
+ "update-return": {
422
+ consoleRole: "tenant-admin",
423
+ oauthScope: "mcp:write",
424
+ readOnly: false
425
+ },
426
+ "return-with-refund": {
427
+ consoleRole: "tenant-admin",
428
+ oauthScope: "mcp:write",
429
+ readOnly: false
430
+ },
431
+ "update-transaction": {
432
+ consoleRole: "tenant-admin",
433
+ oauthScope: "mcp:write",
434
+ readOnly: false
435
+ },
436
+ "update-field-config": {
437
+ consoleRole: "tenant-admin",
438
+ oauthScope: "mcp:write",
439
+ readOnly: false
440
+ },
441
+ "sdk-get-recipe": {
442
+ consoleRole: "tenant-viewer",
443
+ oauthScope: "mcp:read",
444
+ readOnly: true
445
+ },
446
+ "sdk-search-docs": {
447
+ consoleRole: "tenant-viewer",
448
+ oauthScope: "mcp:read",
449
+ readOnly: true
450
+ },
451
+ "sdk-get-auth-setup": {
452
+ consoleRole: "tenant-viewer",
453
+ oauthScope: "mcp:read",
454
+ readOnly: true
455
+ },
456
+ "sdk-get-collection-pattern": {
457
+ consoleRole: "tenant-viewer",
458
+ oauthScope: "mcp:read",
459
+ readOnly: true
460
+ }
461
+ };
462
+ var MCP_TOOL_NAMES = Object.keys(MCP_TOOL_CONTRACT);
463
+ function isMcpToolName(toolName) {
464
+ return Object.prototype.hasOwnProperty.call(MCP_TOOL_CONTRACT, toolName);
465
+ }
466
+
91
467
  // src/tool-policy.ts
92
468
  var READ_ONLY_ANNOTATION = {
93
469
  readOnly: true,
@@ -187,6 +563,13 @@ var TOOL_POLICY_MANIFEST = {
187
563
  consoleSurface: "GET /api/tenants/context",
188
564
  annotationPolicy: READ_ONLY_ANNOTATION
189
565
  },
566
+ "check-feature-progress": {
567
+ category: "read-only-tenant",
568
+ oauthScope: MCP_SCOPES.read,
569
+ consoleRole: "tenant-viewer",
570
+ consoleSurface: "GET /api/tenants/feature-progress",
571
+ annotationPolicy: READ_ONLY_ANNOTATION
572
+ },
190
573
  // ── Cart mutations (mcp:write, tenant-editor) ──
191
574
  "add-cart-item": {
192
575
  category: "mutation-cart",
@@ -236,7 +619,7 @@ var TOOL_POLICY_MANIFEST = {
236
619
  exemptionReason: REASON_CART_EPHEMERAL
237
620
  },
238
621
  // ── Order mutations (mcp:write, tenant-admin) ──
239
- "checkout": {
622
+ checkout: {
240
623
  category: "mutation-order",
241
624
  oauthScope: MCP_SCOPES.write,
242
625
  consoleRole: "tenant-admin",
@@ -344,14 +727,14 @@ var TOOL_POLICY_MANIFEST = {
344
727
  }
345
728
  };
346
729
  function evaluateToolPolicy(toolName, scopes) {
347
- const entry = TOOL_POLICY_MANIFEST[toolName];
348
- if (!entry) {
730
+ if (!isMcpToolName(toolName)) {
349
731
  return {
350
732
  allowed: false,
351
733
  reason: "tool_policy_missing",
352
734
  message: `No tool-policy entry for ${toolName}`
353
735
  };
354
736
  }
737
+ const entry = TOOL_POLICY_MANIFEST[toolName];
355
738
  if (!scopes.includes(entry.oauthScope)) {
356
739
  return {
357
740
  allowed: false,
@@ -362,17 +745,12 @@ function evaluateToolPolicy(toolName, scopes) {
362
745
  return { allowed: true, entry };
363
746
  }
364
747
 
365
- // src/tools/query-collection.ts
366
- import { z } from "zod";
748
+ // src/lib/mcp-telemetry.ts
749
+ import { AsyncLocalStorage as AsyncLocalStorage2 } from "async_hooks";
750
+ import { randomUUID as randomUUID2 } from "crypto";
367
751
 
368
- // src/lib/client.ts
369
- import {
370
- CollectionClient,
371
- CommunityClient,
372
- ModerationApi,
373
- ServerCommerceClient,
374
- createServerClient
375
- } from "@01.software/sdk";
752
+ // src/lib/console-api.ts
753
+ import { createHash } from "crypto";
376
754
 
377
755
  // src/service-auth.ts
378
756
  import { createPrivateKey, randomUUID, sign as signBytes } from "crypto";
@@ -501,43 +879,209 @@ function signMcpServiceToken(context) {
501
879
  return `${signingInput}.${signature.toString("base64url")}`;
502
880
  }
503
881
 
504
- // src/lib/client.ts
882
+ // src/lib/console-api.ts
883
+ var BASE_URL = process.env.SOFTWARE_API_URL || "http://localhost:3000";
884
+ var TIMEOUT_MS = 5e3;
505
885
  var MISSING_HTTP_AUTH_CONTEXT_ERROR = "MCP HTTP requests require a validated OAuth tenant context before tool execution.";
506
- function getClient() {
886
+ function resolveAuthHeaderContext() {
507
887
  const oauthContext = tenantAuthContext();
508
888
  if (oauthContext) {
509
- const serviceToken = signMcpServiceToken(oauthContext);
510
- const client = {
511
- lastRequestId: null,
512
- commerce: void 0,
513
- collections: void 0,
514
- community: void 0
515
- };
516
- const onRequestId = (id) => {
517
- client.lastRequestId = id;
889
+ return {
890
+ apiKey: signMcpServiceToken(oauthContext),
891
+ mode: "oauth"
518
892
  };
519
- client.commerce = new ServerCommerceClient({
520
- secretKey: serviceToken,
521
- onRequestId
522
- });
523
- client.collections = new CollectionClient(
524
- "",
525
- serviceToken,
526
- void 0,
527
- void 0,
528
- onRequestId
893
+ }
894
+ if (hasRequestContext()) throw new Error(MISSING_HTTP_AUTH_CONTEXT_ERROR);
895
+ return {
896
+ apiKey: process.env.SOFTWARE_SECRET_KEY,
897
+ mode: "stdio",
898
+ publishableKey: process.env.SOFTWARE_PUBLISHABLE_KEY ?? process.env.NEXT_PUBLIC_SOFTWARE_PUBLISHABLE_KEY
899
+ };
900
+ }
901
+ function resolveApiKey() {
902
+ const { apiKey } = resolveAuthHeaderContext();
903
+ if (!apiKey || typeof apiKey !== "string") {
904
+ throw new Error(
905
+ "Authentication required. Set SOFTWARE_SECRET_KEY for stdio transport."
529
906
  );
530
- const community = new CommunityClient({ secretKey: serviceToken });
531
- const moderation = new ModerationApi({ secretKey: serviceToken, onRequestId });
532
- client.community = Object.assign(community, {
533
- moderation: {
534
- banCustomer: moderation.banCustomer.bind(moderation),
535
- unbanCustomer: moderation.unbanCustomer.bind(moderation)
536
- }
907
+ }
908
+ return apiKey;
909
+ }
910
+ function buildAuthHeaders(apiKey) {
911
+ const { mode, publishableKey } = resolveAuthHeaderContext();
912
+ const headers = {
913
+ Authorization: `Bearer ${apiKey}`
914
+ };
915
+ if (mode === "stdio" && publishableKey) {
916
+ headers["X-Publishable-Key"] = publishableKey;
917
+ }
918
+ return headers;
919
+ }
920
+ function extractErrorMessage(body) {
921
+ if (!body || typeof body !== "object") return void 0;
922
+ const b = body;
923
+ if (typeof b.error === "string") return b.error;
924
+ if (Array.isArray(b.errors) && b.errors[0]?.message) {
925
+ return String(b.errors[0].message);
926
+ }
927
+ if (typeof b.message === "string") return b.message;
928
+ return void 0;
929
+ }
930
+ async function consoleGet(path, apiKey) {
931
+ const authHeaders = buildAuthHeaders(apiKey);
932
+ const controller = new AbortController();
933
+ const timeoutId = setTimeout(() => controller.abort(), TIMEOUT_MS);
934
+ try {
935
+ const res = await fetch(`${BASE_URL}${path}`, {
936
+ headers: authHeaders,
937
+ signal: controller.signal
537
938
  });
538
- return client;
939
+ if (!res.ok) {
940
+ const body = await res.json().catch(() => ({}));
941
+ const msg = extractErrorMessage(body);
942
+ throw new Error(msg || `Console GET ${path} failed: ${res.status}`);
943
+ }
944
+ return res.json();
945
+ } finally {
946
+ clearTimeout(timeoutId);
539
947
  }
540
- if (hasRequestContext()) throw new Error(MISSING_HTTP_AUTH_CONTEXT_ERROR);
948
+ }
949
+ async function consolePost(path, body, apiKey) {
950
+ const authHeaders = buildAuthHeaders(apiKey);
951
+ const controller = new AbortController();
952
+ const timeoutId = setTimeout(() => controller.abort(), TIMEOUT_MS);
953
+ try {
954
+ const res = await fetch(`${BASE_URL}${path}`, {
955
+ method: "POST",
956
+ headers: { ...authHeaders, "Content-Type": "application/json" },
957
+ body: JSON.stringify(body),
958
+ signal: controller.signal
959
+ });
960
+ if (!res.ok) {
961
+ const errBody = await res.json().catch(() => ({}));
962
+ const msg = extractErrorMessage(errBody);
963
+ throw new Error(msg || `Console POST ${path} failed: ${res.status}`);
964
+ }
965
+ return res.json();
966
+ } finally {
967
+ clearTimeout(timeoutId);
968
+ }
969
+ }
970
+ async function consolePostTelemetry(path, body, apiKey) {
971
+ const authHeaders = buildAuthHeaders(apiKey);
972
+ const controller = new AbortController();
973
+ const timeoutId = setTimeout(() => controller.abort(), TIMEOUT_MS);
974
+ try {
975
+ const res = await fetch(`${BASE_URL}${path}`, {
976
+ method: "POST",
977
+ headers: { ...authHeaders, "Content-Type": "application/json" },
978
+ body: JSON.stringify(body),
979
+ signal: controller.signal
980
+ });
981
+ if (!res.ok) {
982
+ const errBody = await res.json().catch(() => ({}));
983
+ const msg = extractErrorMessage(errBody);
984
+ throw new Error(msg || `Console POST ${path} failed: ${res.status}`);
985
+ }
986
+ } finally {
987
+ clearTimeout(timeoutId);
988
+ }
989
+ }
990
+
991
+ // src/lib/mcp-telemetry.ts
992
+ var TELEMETRY_ENDPOINT = "/api/tenants/mcp-telemetry";
993
+ var FLUSH_TIMEOUT_MS = 1500;
994
+ var telemetryContext = new AsyncLocalStorage2();
995
+ function createMcpTelemetrySummary(transport) {
996
+ return {
997
+ sessionId: randomUUID2(),
998
+ startedAtMs: Date.now(),
999
+ successfulWriteCount: 0,
1000
+ toolCallCount: 0,
1001
+ toolCounts: /* @__PURE__ */ new Map(),
1002
+ transport
1003
+ };
1004
+ }
1005
+ function currentMcpTelemetrySummary() {
1006
+ return telemetryContext.getStore();
1007
+ }
1008
+ function runWithMcpTelemetry(summary, fn) {
1009
+ return telemetryContext.run(summary, fn);
1010
+ }
1011
+ function recordMcpToolResult(params) {
1012
+ if (!isMcpToolName(params.toolName)) return;
1013
+ const toolName = params.toolName;
1014
+ params.summary.toolCallCount += 1;
1015
+ params.summary.toolCounts.set(
1016
+ toolName,
1017
+ (params.summary.toolCounts.get(toolName) ?? 0) + 1
1018
+ );
1019
+ if (!MCP_TOOL_CONTRACT[toolName].readOnly && toolResultSucceeded(params.resultText)) {
1020
+ params.summary.successfulWriteCount += 1;
1021
+ }
1022
+ }
1023
+ function toMcpTelemetryBody(summary) {
1024
+ if (summary.toolCallCount <= 0) return null;
1025
+ const durationMs = summary.transport === "http" ? Math.max(0, summary.durationMs ?? Date.now() - summary.startedAtMs) : void 0;
1026
+ return {
1027
+ converted: summary.successfulWriteCount > 0,
1028
+ ...durationMs !== void 0 ? { durationMs } : {},
1029
+ sessionId: summary.sessionId,
1030
+ successfulWriteCount: summary.successfulWriteCount,
1031
+ toolCallCount: summary.toolCallCount,
1032
+ toolCounts: Object.fromEntries(summary.toolCounts),
1033
+ transport: summary.transport
1034
+ };
1035
+ }
1036
+ async function flushMcpTelemetrySummary(summary) {
1037
+ const body = toMcpTelemetryBody(summary);
1038
+ if (!body) return;
1039
+ await swallow(
1040
+ withTimeout(async () => {
1041
+ const apiKey = resolveApiKey();
1042
+ await consolePostTelemetry(TELEMETRY_ENDPOINT, body, apiKey);
1043
+ }, FLUSH_TIMEOUT_MS)
1044
+ );
1045
+ }
1046
+ function toolResultSucceeded(resultText) {
1047
+ if (!resultText) return false;
1048
+ try {
1049
+ const parsed = JSON.parse(resultText);
1050
+ return parsed.success === true;
1051
+ } catch {
1052
+ return false;
1053
+ }
1054
+ }
1055
+ async function withTimeout(fn, timeoutMs) {
1056
+ let timer;
1057
+ await Promise.race([
1058
+ fn(),
1059
+ new Promise((resolve) => {
1060
+ timer = setTimeout(resolve, timeoutMs);
1061
+ })
1062
+ ]);
1063
+ if (timer) clearTimeout(timer);
1064
+ }
1065
+ async function swallow(promise) {
1066
+ try {
1067
+ await promise;
1068
+ } catch {
1069
+ }
1070
+ }
1071
+
1072
+ // src/tools/query-collection.ts
1073
+ import { z as z3 } from "zod";
1074
+
1075
+ // src/lib/client.ts
1076
+ import { createServerClient } from "@01.software/sdk";
1077
+ var MISSING_HTTP_AUTH_CONTEXT_ERROR2 = "MCP HTTP requests require a validated OAuth tenant context before tool execution.";
1078
+ var HTTP_OAUTH_SDK_CLIENT_ERROR = "MCP HTTP OAuth requests cannot use SDK-backed tools. Use reviewed Console service endpoints for OAuth transport.";
1079
+ function getClient() {
1080
+ const oauthContext = tenantAuthContext();
1081
+ if (oauthContext) {
1082
+ throw new Error(HTTP_OAUTH_SDK_CLIENT_ERROR);
1083
+ }
1084
+ if (hasRequestContext()) throw new Error(MISSING_HTTP_AUTH_CONTEXT_ERROR2);
541
1085
  const secretKey = process.env.SOFTWARE_SECRET_KEY;
542
1086
  const publishableKey = process.env.SOFTWARE_PUBLISHABLE_KEY || process.env.NEXT_PUBLIC_SOFTWARE_PUBLISHABLE_KEY;
543
1087
  if (!secretKey) {
@@ -560,15 +1104,18 @@ function getClient() {
560
1104
  }
561
1105
 
562
1106
  // src/tools/query-collection.ts
563
- import { COLLECTIONS } from "@01.software/sdk";
1107
+ import { SERVER_COLLECTIONS } from "@01.software/sdk";
564
1108
  var schema = {
565
- collection: z.enum(COLLECTIONS).describe("Collection name (required)"),
566
- where: z.string().optional().describe(
1109
+ collection: z3.enum(SERVER_COLLECTIONS).describe("Collection name (required)"),
1110
+ where: z3.string().optional().describe(
567
1111
  `Filter conditions (JSON string, optional). Pass the Payload query condition object as a JSON string. Example: '{"title":{"equals":"Product name"}}'`
568
1112
  ),
569
- limit: z.number().min(1).max(100).default(10).describe("Maximum number of items to return (1-100, default: 10)."),
570
- page: z.number().optional().describe("Page number (optional). Starts from 1. Used for pagination."),
571
- sort: z.string().regex(/^-?[a-zA-Z0-9_.]+$/, 'Sort must be a field name, optionally prefixed with "-" for descending').optional().describe(
1113
+ limit: z3.number().min(1).max(100).default(10).describe("Maximum number of items to return (1-100, default: 10)."),
1114
+ page: z3.number().optional().describe("Page number (optional). Starts from 1. Used for pagination."),
1115
+ sort: z3.string().regex(
1116
+ /^-?[a-zA-Z0-9_.]+$/,
1117
+ 'Sort must be a field name, optionally prefixed with "-" for descending'
1118
+ ).optional().describe(
572
1119
  'Sort field (optional). Use "fieldName" for ascending or "-fieldName" for descending. Example: "createdAt" or "-createdAt"'
573
1120
  )
574
1121
  };
@@ -622,11 +1169,11 @@ async function queryCollection({
622
1169
  }
623
1170
 
624
1171
  // src/tools/get-collection-by-id.ts
625
- import { z as z2 } from "zod";
626
- import { COLLECTIONS as COLLECTIONS2 } from "@01.software/sdk";
1172
+ import { z as z4 } from "zod";
1173
+ import { SERVER_COLLECTIONS as SERVER_COLLECTIONS2 } from "@01.software/sdk";
627
1174
  var schema2 = {
628
- collection: z2.enum(COLLECTIONS2).describe("Collection name (required)"),
629
- id: z2.string().min(1).describe("Item ID (required)")
1175
+ collection: z4.enum(SERVER_COLLECTIONS2).describe("Collection name (required)"),
1176
+ id: z4.string().min(1).describe("Item ID (required)")
630
1177
  };
631
1178
  var metadata2 = {
632
1179
  name: "get-collection-by-id",
@@ -652,9 +1199,9 @@ async function getCollectionById({
652
1199
  }
653
1200
 
654
1201
  // src/tools/get-order.ts
655
- import { z as z3 } from "zod";
1202
+ import { z as z5 } from "zod";
656
1203
  var schema3 = {
657
- orderNumber: z3.string().min(1).describe("Order number to look up (required)")
1204
+ orderNumber: z5.string().min(1).describe("Order number to look up (required)")
658
1205
  };
659
1206
  var metadata3 = {
660
1207
  name: "get-order",
@@ -684,24 +1231,24 @@ async function getOrder({
684
1231
  }
685
1232
 
686
1233
  // src/tools/create-order.ts
687
- import { z as z4 } from "zod";
1234
+ import { z as z6 } from "zod";
688
1235
  var schema4 = {
689
- pgPaymentId: z4.string().optional().describe("PG payment ID (optional \u2014 omit for free orders)"),
690
- orderNumber: z4.string().min(1).describe("Unique order number (required)"),
691
- customerSnapshot: z4.object({
692
- name: z4.string().optional().describe("Customer name"),
693
- email: z4.string().describe("Customer email (required)"),
694
- phone: z4.string().optional().describe("Customer phone")
1236
+ pgPaymentId: z6.string().optional().describe("PG payment ID (optional \u2014 omit for free orders)"),
1237
+ orderNumber: z6.string().min(1).describe("Unique order number (required)"),
1238
+ customerSnapshot: z6.object({
1239
+ name: z6.string().optional().describe("Customer name"),
1240
+ email: z6.string().describe("Customer email (required)"),
1241
+ phone: z6.string().optional().describe("Customer phone")
695
1242
  }).describe("Customer snapshot at time of order (required)"),
696
- shippingAddress: z4.record(z4.string(), z4.unknown()).describe(
1243
+ shippingAddress: z6.record(z6.string(), z6.unknown()).describe(
697
1244
  "Shipping address object (required). Fields: postalCode, address1, address2, deliveryMessage, recipientName, phone"
698
1245
  ),
699
- orderItems: z4.array(z4.record(z4.string(), z4.unknown())).describe(
1246
+ orderItems: z6.array(z6.record(z6.string(), z6.unknown())).describe(
700
1247
  "Array of order item objects (required). Each: { product, variant, option, quantity, unitPrice?, totalPrice? }"
701
1248
  ),
702
- totalAmount: z4.number().nonnegative().describe("Total order amount (required, min 0)"),
703
- shippingAmount: z4.number().nonnegative().optional().describe("Shipping amount (optional, default 0)"),
704
- discountCode: z4.string().optional().describe("Discount code to apply (optional)")
1249
+ totalAmount: z6.number().nonnegative().describe("Total order amount (required, min 0)"),
1250
+ shippingAmount: z6.number().nonnegative().optional().describe("Shipping amount (optional, default 0)"),
1251
+ discountCode: z6.string().optional().describe("Discount code to apply (optional)")
705
1252
  };
706
1253
  var metadata4 = {
707
1254
  name: "create-order",
@@ -726,10 +1273,10 @@ async function createOrder(params) {
726
1273
  }
727
1274
 
728
1275
  // src/tools/update-order.ts
729
- import { z as z5 } from "zod";
1276
+ import { z as z7 } from "zod";
730
1277
  var schema5 = {
731
- orderNumber: z5.string().min(1).describe("Order number (required)"),
732
- status: z5.enum([
1278
+ orderNumber: z7.string().min(1).describe("Order number (required)"),
1279
+ status: z7.enum([
733
1280
  "pending",
734
1281
  "paid",
735
1282
  "failed",
@@ -766,15 +1313,15 @@ async function updateOrder({
766
1313
  }
767
1314
 
768
1315
  // src/tools/checkout.ts
769
- import { z as z6 } from "zod";
1316
+ import { z as z8 } from "zod";
770
1317
  var schema6 = {
771
- cartId: z6.string().min(1).describe("Cart ID to convert to order (required)"),
772
- pgPaymentId: z6.string().optional().describe("PG payment ID (optional \u2014 omit for free orders)"),
773
- orderNumber: z6.string().min(1).describe("Unique order number (required)"),
774
- customerSnapshot: z6.record(z6.string(), z6.unknown()).describe(
1318
+ cartId: z8.string().min(1).describe("Cart ID to convert to order (required)"),
1319
+ pgPaymentId: z8.string().optional().describe("PG payment ID (optional \u2014 omit for free orders)"),
1320
+ orderNumber: z8.string().min(1).describe("Unique order number (required)"),
1321
+ customerSnapshot: z8.record(z8.string(), z8.unknown()).describe(
775
1322
  "Customer snapshot object (required). Fields: { name?, email, phone? }"
776
1323
  ),
777
- discountCode: z6.string().optional().describe("Discount code to apply (optional)")
1324
+ discountCode: z8.string().optional().describe("Discount code to apply (optional)")
778
1325
  };
779
1326
  var metadata6 = {
780
1327
  name: "checkout",
@@ -799,17 +1346,17 @@ async function checkout(params) {
799
1346
  }
800
1347
 
801
1348
  // src/tools/create-fulfillment.ts
802
- import { z as z7 } from "zod";
1349
+ import { z as z9 } from "zod";
803
1350
  var schema7 = {
804
- orderNumber: z7.string().min(1).describe("Order number (required)"),
805
- carrier: z7.string().optional().describe("Shipping carrier name (optional)"),
806
- trackingNumber: z7.string().optional().describe(
1351
+ orderNumber: z9.string().min(1).describe("Order number (required)"),
1352
+ carrier: z9.string().optional().describe("Shipping carrier name (optional)"),
1353
+ trackingNumber: z9.string().optional().describe(
807
1354
  'Tracking number (optional). Setting carrier + tracking triggers "shipped" status'
808
1355
  ),
809
- items: z7.array(
810
- z7.object({
811
- orderItem: z7.string().min(1).describe("Order item ID"),
812
- quantity: z7.number().int().positive().describe("Quantity to fulfill")
1356
+ items: z9.array(
1357
+ z9.object({
1358
+ orderItem: z9.string().min(1).describe("Order item ID"),
1359
+ quantity: z9.number().int().positive().describe("Quantity to fulfill")
813
1360
  })
814
1361
  ).describe("Array of items to fulfill (required)")
815
1362
  };
@@ -844,16 +1391,16 @@ async function createFulfillment({
844
1391
  }
845
1392
 
846
1393
  // src/tools/update-fulfillment.ts
847
- import { z as z8 } from "zod";
1394
+ import { z as z10 } from "zod";
848
1395
  var schema8 = {
849
- fulfillmentId: z8.string().min(1).describe("Fulfillment ID (required)"),
850
- status: z8.enum(["packed", "shipped", "delivered", "failed"]).describe(
1396
+ fulfillmentId: z10.string().min(1).describe("Fulfillment ID (required)"),
1397
+ status: z10.enum(["packed", "shipped", "delivered", "failed"]).describe(
851
1398
  "New fulfillment status (required). FSM: pending\u2192packed/shipped/failed, packed\u2192shipped/failed, shipped\u2192delivered/failed"
852
1399
  ),
853
- carrier: z8.string().optional().describe(
1400
+ carrier: z10.string().optional().describe(
854
1401
  "Shipping carrier (optional, changeable only in pending/packed status)"
855
1402
  ),
856
- trackingNumber: z8.string().optional().describe(
1403
+ trackingNumber: z10.string().optional().describe(
857
1404
  "Tracking number (optional, changeable only in pending/packed status)"
858
1405
  )
859
1406
  };
@@ -887,131 +1434,6 @@ async function updateFulfillment({
887
1434
  }
888
1435
  }
889
1436
 
890
- // ../../packages/contracts/src/tenant/index.ts
891
- import { z as z9 } from "zod";
892
- var tenantFieldConfigStateSchema = z9.object({
893
- hiddenFields: z9.array(z9.string()),
894
- isHidden: z9.boolean()
895
- }).strict();
896
- var tenantContextQuerySchema = z9.object({
897
- counts: z9.literal("true").optional()
898
- }).strict();
899
- var tenantContextToolInputSchema = z9.object({
900
- includeCounts: z9.boolean().optional().default(false).describe(
901
- "Include per-collection document counts and config status (bypasses cache, slower)"
902
- )
903
- }).strict();
904
- var tenantContextResponseSchema = z9.object({
905
- tenant: z9.object({
906
- id: z9.string(),
907
- name: z9.string(),
908
- plan: z9.string(),
909
- planSource: z9.string().optional(),
910
- authoritative: z9.boolean().optional(),
911
- capabilityVersion: z9.string().optional(),
912
- isDevMode: z9.boolean()
913
- }).strict(),
914
- features: z9.array(z9.string()),
915
- collections: z9.object({
916
- active: z9.array(z9.string()),
917
- inactive: z9.array(z9.string())
918
- }).strict(),
919
- fieldConfigs: z9.record(z9.string(), tenantFieldConfigStateSchema),
920
- counts: z9.record(z9.string(), z9.number()).optional(),
921
- config: z9.object({
922
- webhookConfigured: z9.boolean()
923
- }).strict().optional()
924
- }).strict();
925
- var COLLECTION_SCHEMA_CONTRACT_VERSION = 1;
926
- var collectionSchemaEndpointParamsSchema = z9.object({
927
- collectionSlug: z9.string().min(1, "collectionSlug is required")
928
- }).strict();
929
- function createCollectionSchemaToolInputSchema(collections) {
930
- return z9.object({
931
- collection: z9.enum(collections).describe("Collection name (required)")
932
- }).strict();
933
- }
934
- var collectionFieldOptionSchema = z9.object({
935
- label: z9.string(),
936
- value: z9.string()
937
- }).strict();
938
- var collectionFieldSchema = z9.lazy(
939
- () => z9.object({
940
- name: z9.string(),
941
- path: z9.string(),
942
- type: z9.string(),
943
- required: z9.literal(true).optional(),
944
- unique: z9.literal(true).optional(),
945
- hasMany: z9.literal(true).optional(),
946
- relationTo: z9.union([z9.string(), z9.array(z9.string())]).optional(),
947
- options: z9.array(collectionFieldOptionSchema).optional(),
948
- hidden: z9.literal(true).optional(),
949
- systemManaged: z9.literal(true).optional(),
950
- writable: z9.boolean().optional(),
951
- fields: z9.array(collectionFieldSchema).optional()
952
- }).strict()
953
- );
954
- var collectionSchemaResponseSchema = z9.object({
955
- contractVersion: z9.literal(COLLECTION_SCHEMA_CONTRACT_VERSION),
956
- mode: z9.literal("effective"),
957
- collection: z9.object({
958
- slug: z9.string(),
959
- timestamps: z9.boolean(),
960
- alwaysActive: z9.boolean(),
961
- feature: z9.string().nullable(),
962
- systemFields: z9.array(z9.string()),
963
- visibility: z9.object({
964
- collectionHidden: z9.boolean(),
965
- hiddenFields: z9.array(z9.string())
966
- }).strict(),
967
- fields: z9.array(collectionFieldSchema)
968
- }).strict()
969
- }).strict();
970
-
971
- // ../../packages/contracts/src/ecommerce/index.ts
972
- import { z as z10 } from "zod";
973
- var transactionStatusSchema = z10.enum([
974
- "pending",
975
- "paid",
976
- "failed",
977
- "canceled"
978
- ]);
979
- var updateTransactionSchema = z10.object({
980
- pgPaymentId: z10.string().min(1, "pgPaymentId is required").describe("PG payment ID (required)"),
981
- status: transactionStatusSchema.describe(
982
- "New transaction status (required)"
983
- ),
984
- paymentMethod: z10.string().optional().describe("Payment method (optional)"),
985
- receiptUrl: z10.string().optional().describe("Receipt URL (optional)"),
986
- paymentKey: z10.string().min(1).optional().describe("Provider payment key for verified paid confirmation"),
987
- amount: z10.number().int().positive().optional().describe("Provider-confirmed amount for verified paid confirmation")
988
- }).strict();
989
- var UpdateTransactionSchema = updateTransactionSchema;
990
- var returnReasonSchema = z10.enum([
991
- "change_of_mind",
992
- "defective",
993
- "wrong_delivery",
994
- "damaged",
995
- "other"
996
- ]);
997
- var restockActionSchema = z10.enum(["return_to_stock", "discard"]);
998
- var returnWithRefundItemSchema = z10.object({
999
- orderItem: z10.union([z10.string(), z10.number()]).transform(String),
1000
- quantity: z10.number().int().positive("quantity must be a positive integer"),
1001
- restockAction: restockActionSchema.default("return_to_stock")
1002
- }).strict();
1003
- var returnWithRefundSchema = z10.object({
1004
- orderNumber: z10.string().min(1, "orderNumber is required").describe("Order number (required)"),
1005
- reason: returnReasonSchema.optional().describe("Return reason (optional)"),
1006
- reasonDetail: z10.string().optional().describe("Detailed reason text (optional)"),
1007
- returnItems: z10.array(returnWithRefundItemSchema).min(1, "At least one return item is required").max(100, "Too many return items").describe("Array of products to return (required)"),
1008
- refundAmount: z10.number().min(0, "refundAmount must be non-negative").describe("Refund amount (required, min 0)"),
1009
- pgPaymentId: z10.string().min(1, "pgPaymentId is required").describe("PG payment ID for refund (required)"),
1010
- paymentKey: z10.string().min(1).optional().describe("Provider payment key for verified refund"),
1011
- refundReceiptUrl: z10.string().optional().describe("Refund receipt URL (optional)")
1012
- }).strict();
1013
- var ReturnWithRefundSchema = returnWithRefundSchema;
1014
-
1015
1437
  // src/tools/update-transaction.ts
1016
1438
  var schema9 = UpdateTransactionSchema.shape;
1017
1439
  var metadata9 = {
@@ -1404,143 +1826,53 @@ async function calculateShipping({
1404
1826
  try {
1405
1827
  const client = getClient();
1406
1828
  const result = await client.commerce.shipping.calculate({
1407
- shippingPolicyId,
1408
- orderAmount,
1409
- postalCode
1410
- });
1411
- return toolSuccess({ data: result });
1412
- } catch (error) {
1413
- return toolError(error);
1414
- }
1415
- }
1416
-
1417
- // src/tools/stock-check.ts
1418
- import { z as z21 } from "zod";
1419
- var schema21 = {
1420
- items: z21.array(
1421
- z21.object({
1422
- variantId: z21.string().describe("Product variant ID"),
1423
- quantity: z21.number().int().positive().describe("Requested quantity")
1424
- })
1425
- ).describe(
1426
- "Array of items to check stock for (required, max 100). Each: { variantId, quantity }"
1427
- )
1428
- };
1429
- var metadata21 = {
1430
- name: "stock-check",
1431
- description: "Batch check product option stock availability. Returns per-item availability and an allAvailable flag.",
1432
- annotations: {
1433
- title: "Check stock availability",
1434
- readOnlyHint: true,
1435
- destructiveHint: false,
1436
- idempotentHint: true
1437
- }
1438
- };
1439
- async function stockCheck({
1440
- items
1441
- }) {
1442
- try {
1443
- const client = getClient();
1444
- const result = await client.commerce.product.stockCheck({ items });
1445
- return toolSuccess({ data: result });
1446
- } catch (error) {
1447
- return toolError(error);
1448
- }
1449
- }
1450
-
1451
- // src/tools/get-collection-schema.ts
1452
- import { COLLECTIONS as COLLECTIONS3 } from "@01.software/sdk";
1453
-
1454
- // src/lib/console-api.ts
1455
- import { createHash } from "crypto";
1456
- var BASE_URL = process.env.SOFTWARE_API_URL || "http://localhost:3000";
1457
- var TIMEOUT_MS = 5e3;
1458
- var MISSING_HTTP_AUTH_CONTEXT_ERROR2 = "MCP HTTP requests require a validated OAuth tenant context before tool execution.";
1459
- function resolveAuthHeaderContext() {
1460
- const oauthContext = tenantAuthContext();
1461
- if (oauthContext) {
1462
- return {
1463
- apiKey: signMcpServiceToken(oauthContext),
1464
- mode: "oauth"
1465
- };
1466
- }
1467
- if (hasRequestContext()) throw new Error(MISSING_HTTP_AUTH_CONTEXT_ERROR2);
1468
- return {
1469
- apiKey: process.env.SOFTWARE_SECRET_KEY,
1470
- mode: "stdio",
1471
- publishableKey: process.env.SOFTWARE_PUBLISHABLE_KEY ?? process.env.NEXT_PUBLIC_SOFTWARE_PUBLISHABLE_KEY
1472
- };
1473
- }
1474
- function resolveApiKey() {
1475
- const { apiKey } = resolveAuthHeaderContext();
1476
- if (!apiKey || typeof apiKey !== "string") {
1477
- throw new Error(
1478
- "Authentication required. Set SOFTWARE_SECRET_KEY for stdio transport."
1479
- );
1480
- }
1481
- return apiKey;
1482
- }
1483
- function buildAuthHeaders(apiKey) {
1484
- const { mode, publishableKey } = resolveAuthHeaderContext();
1485
- const headers = {
1486
- Authorization: `Bearer ${apiKey}`
1487
- };
1488
- if (mode === "stdio" && publishableKey) {
1489
- headers["X-Publishable-Key"] = publishableKey;
1490
- }
1491
- return headers;
1492
- }
1493
- function extractErrorMessage(body) {
1494
- if (!body || typeof body !== "object") return void 0;
1495
- const b = body;
1496
- if (typeof b.error === "string") return b.error;
1497
- if (Array.isArray(b.errors) && b.errors[0]?.message) {
1498
- return String(b.errors[0].message);
1499
- }
1500
- if (typeof b.message === "string") return b.message;
1501
- return void 0;
1502
- }
1503
- async function consoleGet(path, apiKey) {
1504
- const authHeaders = buildAuthHeaders(apiKey);
1505
- const controller = new AbortController();
1506
- const timeoutId = setTimeout(() => controller.abort(), TIMEOUT_MS);
1507
- try {
1508
- const res = await fetch(`${BASE_URL}${path}`, {
1509
- headers: authHeaders,
1510
- signal: controller.signal
1829
+ shippingPolicyId,
1830
+ orderAmount,
1831
+ postalCode
1511
1832
  });
1512
- if (!res.ok) {
1513
- const body = await res.json().catch(() => ({}));
1514
- const msg = extractErrorMessage(body);
1515
- throw new Error(msg || `Console GET ${path} failed: ${res.status}`);
1516
- }
1517
- return res.json();
1518
- } finally {
1519
- clearTimeout(timeoutId);
1833
+ return toolSuccess({ data: result });
1834
+ } catch (error) {
1835
+ return toolError(error);
1520
1836
  }
1521
1837
  }
1522
- async function consolePost(path, body, apiKey) {
1523
- const authHeaders = buildAuthHeaders(apiKey);
1524
- const controller = new AbortController();
1525
- const timeoutId = setTimeout(() => controller.abort(), TIMEOUT_MS);
1838
+
1839
+ // src/tools/stock-check.ts
1840
+ import { z as z21 } from "zod";
1841
+ var schema21 = {
1842
+ items: z21.array(
1843
+ z21.object({
1844
+ variantId: z21.string().describe("Product variant ID"),
1845
+ quantity: z21.number().int().positive().describe("Requested quantity")
1846
+ })
1847
+ ).describe(
1848
+ "Array of items to check stock for (required, max 100). Each: { variantId, quantity }"
1849
+ )
1850
+ };
1851
+ var metadata21 = {
1852
+ name: "stock-check",
1853
+ description: "Batch check product option stock availability. Returns per-item availability and an allAvailable flag.",
1854
+ annotations: {
1855
+ title: "Check stock availability",
1856
+ readOnlyHint: true,
1857
+ destructiveHint: false,
1858
+ idempotentHint: true
1859
+ }
1860
+ };
1861
+ async function stockCheck({
1862
+ items
1863
+ }) {
1526
1864
  try {
1527
- const res = await fetch(`${BASE_URL}${path}`, {
1528
- method: "POST",
1529
- headers: { ...authHeaders, "Content-Type": "application/json" },
1530
- body: JSON.stringify(body),
1531
- signal: controller.signal
1532
- });
1533
- if (!res.ok) {
1534
- const errBody = await res.json().catch(() => ({}));
1535
- const msg = extractErrorMessage(errBody);
1536
- throw new Error(msg || `Console POST ${path} failed: ${res.status}`);
1537
- }
1538
- return res.json();
1539
- } finally {
1540
- clearTimeout(timeoutId);
1865
+ const client = getClient();
1866
+ const result = await client.commerce.product.stockCheck({ items });
1867
+ return toolSuccess({ data: result });
1868
+ } catch (error) {
1869
+ return toolError(error);
1541
1870
  }
1542
1871
  }
1543
1872
 
1873
+ // src/tools/get-collection-schema.ts
1874
+ import { SERVER_COLLECTIONS as SERVER_COLLECTIONS3 } from "@01.software/sdk";
1875
+
1544
1876
  // src/lib/collection-schema.ts
1545
1877
  async function getCollectionSchema(collection) {
1546
1878
  const apiKey = resolveApiKey();
@@ -1552,7 +1884,7 @@ async function getCollectionSchema(collection) {
1552
1884
  }
1553
1885
 
1554
1886
  // src/tools/get-collection-schema.ts
1555
- var schema22 = createCollectionSchemaToolInputSchema(COLLECTIONS3).shape;
1887
+ var schema22 = createCollectionSchemaToolInputSchema(SERVER_COLLECTIONS3).shape;
1556
1888
  var metadata22 = {
1557
1889
  name: "get-collection-schema",
1558
1890
  description: "Get the authoritative tenant-aware collection schema from console. Use this before create/update to understand writable fields, hidden fields, required metadata, and collection-level visibility.",
@@ -1581,6 +1913,11 @@ async function getCollectionSchemaTool({
1581
1913
  function getTenantContextPath(includeCounts) {
1582
1914
  return includeCounts ? "/api/tenants/context?counts=true" : "/api/tenants/context";
1583
1915
  }
1916
+ function getTenantFeatureProgressPath(feature, includeEvidence) {
1917
+ const search = new URLSearchParams({ feature });
1918
+ if (includeEvidence) search.set("includeEvidence", "true");
1919
+ return `/api/tenants/feature-progress?${search.toString()}`;
1920
+ }
1584
1921
  async function getTenantContext(includeCounts = false) {
1585
1922
  const apiKey = resolveApiKey();
1586
1923
  const data = await consoleGet(
@@ -1589,6 +1926,14 @@ async function getTenantContext(includeCounts = false) {
1589
1926
  );
1590
1927
  return tenantContextResponseSchema.parse(data);
1591
1928
  }
1929
+ async function getTenantFeatureProgress(feature, includeEvidence = false) {
1930
+ const apiKey = resolveApiKey();
1931
+ const data = await consoleGet(
1932
+ getTenantFeatureProgressPath(feature, includeEvidence),
1933
+ apiKey
1934
+ );
1935
+ return tenantFeatureProgressResponseSchema.parse(data);
1936
+ }
1592
1937
 
1593
1938
  // src/tools/get-tenant-context.ts
1594
1939
  var schema23 = tenantContextToolInputSchema.shape;
@@ -1668,6 +2013,30 @@ async function handler({
1668
2013
  }
1669
2014
  }
1670
2015
 
2016
+ // src/tools/check-feature-progress.ts
2017
+ var schema24 = tenantFeatureProgressInputSchema.shape;
2018
+ var metadata24 = {
2019
+ name: "check-feature-progress",
2020
+ description: "Check tenant implementation progress for a supported feature. Start with feature=ecommerce to inspect catalog, cart, checkout, payment result, webhook, and operations readiness without mutating tenant data.",
2021
+ annotations: {
2022
+ title: "Check Feature Progress",
2023
+ readOnlyHint: true,
2024
+ destructiveHint: false,
2025
+ idempotentHint: true
2026
+ }
2027
+ };
2028
+ async function handler2({
2029
+ feature,
2030
+ includeEvidence
2031
+ }) {
2032
+ try {
2033
+ const progress = await getTenantFeatureProgress(feature, includeEvidence);
2034
+ return toolSuccess({ progress });
2035
+ } catch (error) {
2036
+ return toolError(error);
2037
+ }
2038
+ }
2039
+
1671
2040
  // src/tools/list-configurable-fields.ts
1672
2041
  import { z as z22 } from "zod";
1673
2042
 
@@ -1692,12 +2061,12 @@ function invalidateFieldConfigCache() {
1692
2061
  }
1693
2062
 
1694
2063
  // src/tools/list-configurable-fields.ts
1695
- var schema24 = {
2064
+ var schema25 = {
1696
2065
  collection: z22.string().optional().describe(
1697
2066
  "Filter by collection slug (optional \u2014 returns all if omitted). Use this filter to reduce response size when you know which collection to check."
1698
2067
  )
1699
2068
  };
1700
- var metadata24 = {
2069
+ var metadata25 = {
1701
2070
  name: "list-configurable-fields",
1702
2071
  description: "List all configurable fields for tenant collections with current visibility state. Shows which fields can be shown/hidden and their current status. Returns all collections including inactive features \u2014 cross-reference with get-tenant-context for active features. Response includes ~300 fields across 47 collections \u2014 use collection filter when possible.",
1703
2072
  annotations: {
@@ -1729,7 +2098,7 @@ async function listConfigurableFields(params) {
1729
2098
 
1730
2099
  // src/tools/update-field-config.ts
1731
2100
  import { z as z23 } from "zod";
1732
- var schema25 = {
2101
+ var schema26 = {
1733
2102
  collection: z23.string().min(1).describe("Collection slug (required)"),
1734
2103
  hiddenFields: z23.array(z23.string().min(1).max(200)).max(300).describe(
1735
2104
  "Fields to hide (required). This is a FULL REPLACE \u2014 fields NOT in this list will be shown. Pass [] to show all fields. Use list-configurable-fields first to see available field paths."
@@ -1738,7 +2107,7 @@ var schema25 = {
1738
2107
  "Hide the entire collection from Admin Panel (optional). When true, individual hiddenFields are irrelevant."
1739
2108
  )
1740
2109
  };
1741
- var metadata25 = {
2110
+ var metadata26 = {
1742
2111
  name: "update-field-config",
1743
2112
  description: "Update field visibility configuration for a tenant collection. Hidden fields are removed from the Admin Panel UI. IMPORTANT: hiddenFields is a full replace, not a merge. Always call list-configurable-fields first to see current state.",
1744
2113
  annotations: {
@@ -2198,7 +2567,7 @@ function getRecipe(goal, runtime = "both") {
2198
2567
  }
2199
2568
 
2200
2569
  // src/tools/sdk-get-recipe.ts
2201
- var schema26 = {
2570
+ var schema27 = {
2202
2571
  goal: z24.enum([
2203
2572
  "fetch-list",
2204
2573
  "fetch-by-id",
@@ -2215,7 +2584,7 @@ var schema26 = {
2215
2584
  collection: z24.string().optional().describe("Specific collection name if applicable"),
2216
2585
  includeExample: z24.boolean().default(true).describe("Whether to include a full code example")
2217
2586
  };
2218
- var metadata26 = {
2587
+ var metadata27 = {
2219
2588
  name: "sdk-get-recipe",
2220
2589
  description: "Get a complete SDK code recipe for a specific task. Returns recommended approach, code example, and related documentation links. Use this FIRST when the user asks how to do something with the SDK.",
2221
2590
  annotations: {
@@ -2225,7 +2594,7 @@ var metadata26 = {
2225
2594
  idempotentHint: true
2226
2595
  }
2227
2596
  };
2228
- function handler2({
2597
+ function handler3({
2229
2598
  goal,
2230
2599
  runtime,
2231
2600
  collection,
@@ -2272,7 +2641,7 @@ var docIndex = [
2272
2641
  {
2273
2642
  title: "Browser Client vs Server Client",
2274
2643
  keywords: ["browser", "server", "publishable key", "secret key", "createClient", "createServerClient", "NEXT_PUBLIC_SOFTWARE_PUBLISHABLE_KEY", "SOFTWARE_PUBLISHABLE_KEY", "SOFTWARE_SECRET_KEY", "pk01_", "sk01_", "pat01_", "read-only", "full crud"],
2275
- summary: "createClient() for browser with publishableKey (read-only pk01_), createServerClient() for server with SOFTWARE_SECRET_KEY (usually sk01_, sometimes pat01_ in browser-auth-scoped flows). Never expose SECRET_KEY to the browser.",
2644
+ summary: "createClient() for browser with publishableKey (read-only pk01_), createServerClient() for server with matching SOFTWARE_PUBLISHABLE_KEY + SOFTWARE_SECRET_KEY (usually sk01_, sometimes pat01_ in scoped flows). Never expose SECRET_KEY to the browser.",
2276
2645
  resourceUri: "docs://sdk/getting-started"
2277
2646
  },
2278
2647
  // Query Builder
@@ -2433,11 +2802,11 @@ function searchDocs(query, limit = 5) {
2433
2802
  }
2434
2803
 
2435
2804
  // src/tools/sdk-search-docs.ts
2436
- var schema27 = {
2805
+ var schema28 = {
2437
2806
  query: z25.string().min(2).describe('Search keyword or phrase (e.g. "infinite scroll", "webhook", "customer login")'),
2438
2807
  limit: z25.number().min(1).max(10).default(5).describe("Maximum results to return (1-10, default: 5)")
2439
2808
  };
2440
- var metadata27 = {
2809
+ var metadata28 = {
2441
2810
  name: "sdk-search-docs",
2442
2811
  description: "Search SDK documentation by keyword. Returns matching topics with summaries and resource links. Use when looking for specific SDK features or patterns.",
2443
2812
  annotations: {
@@ -2447,7 +2816,7 @@ var metadata27 = {
2447
2816
  idempotentHint: true
2448
2817
  }
2449
2818
  };
2450
- function handler3({
2819
+ function handler4({
2451
2820
  query,
2452
2821
  limit
2453
2822
  }) {
@@ -2473,7 +2842,7 @@ function handler3({
2473
2842
 
2474
2843
  // src/tools/sdk-get-auth-setup.ts
2475
2844
  import { z as z26 } from "zod";
2476
- var schema28 = {
2845
+ var schema29 = {
2477
2846
  scenario: z26.enum([
2478
2847
  "browser-client",
2479
2848
  "server-client",
@@ -2483,7 +2852,7 @@ var schema28 = {
2483
2852
  "webhook-verification"
2484
2853
  ]).describe("Authentication scenario")
2485
2854
  };
2486
- var metadata28 = {
2855
+ var metadata29 = {
2487
2856
  name: "sdk-get-auth-setup",
2488
2857
  description: "Get the current authentication setup for a specific scenario. Returns env var names, code snippets, and security notes.",
2489
2858
  annotations: {
@@ -2622,7 +2991,7 @@ export async function POST(request: Request) {
2622
2991
  ]
2623
2992
  }
2624
2993
  };
2625
- function handler4({
2994
+ function handler5({
2626
2995
  scenario
2627
2996
  }) {
2628
2997
  try {
@@ -2638,13 +3007,13 @@ function handler4({
2638
3007
 
2639
3008
  // src/tools/sdk-get-collection-pattern.ts
2640
3009
  import { z as z27 } from "zod";
2641
- import { COLLECTIONS as COLLECTIONS4 } from "@01.software/sdk";
2642
- var schema29 = {
2643
- collection: z27.enum(COLLECTIONS4).describe("Collection name"),
3010
+ import { COLLECTIONS, SERVER_COLLECTIONS as SERVER_COLLECTIONS4 } from "@01.software/sdk";
3011
+ var schema30 = {
3012
+ collection: z27.enum(SERVER_COLLECTIONS4).describe("Collection name"),
2644
3013
  operation: z27.enum(["read", "write", "full-crud"]).default("read").describe("What operations are needed"),
2645
3014
  surface: z27.enum(["query-builder", "react-query", "server-api"]).default("query-builder").describe("Preferred API surface")
2646
3015
  };
2647
- var metadata29 = {
3016
+ var metadata30 = {
2648
3017
  name: "sdk-get-collection-pattern",
2649
3018
  description: "Get the recommended CRUD pattern for a specific collection. Returns code examples for the chosen API surface and operation type.",
2650
3019
  annotations: {
@@ -2655,7 +3024,15 @@ var metadata29 = {
2655
3024
  }
2656
3025
  };
2657
3026
  function generatePattern(collection, operation, surface) {
3027
+ const isPublicCollection = COLLECTIONS.includes(
3028
+ collection
3029
+ );
2658
3030
  if (surface === "react-query") {
3031
+ if (!isPublicCollection) {
3032
+ throw new Error(
3033
+ `${collection} is server-only. Use surface="server-api" with createServerClient().`
3034
+ );
3035
+ }
2659
3036
  const parts2 = [];
2660
3037
  if (operation === "read") {
2661
3038
  parts2.push(
@@ -2767,17 +3144,29 @@ function generatePattern(collection, operation, surface) {
2767
3144
  }
2768
3145
  const parts = [];
2769
3146
  if (operation === "read" || operation === "full-crud") {
2770
- parts.push(
2771
- `// Read with any client (Client or ServerClient)`,
2772
- `const result = await client.collections.from('${collection}').find({`,
2773
- ` where: { status: { equals: 'published' } },`,
2774
- ` limit: 10,`,
2775
- ` sort: '-createdAt'`,
2776
- `})`,
2777
- ``,
2778
- `const item = await client.collections.from('${collection}').findById(id)`,
2779
- `const { totalDocs } = await client.collections.from('${collection}').count()`
2780
- );
3147
+ if (isPublicCollection) {
3148
+ parts.push(
3149
+ `// Read with any client (Client or ServerClient)`,
3150
+ `const result = await client.collections.from('${collection}').find({`,
3151
+ ` where: { status: { equals: 'published' } },`,
3152
+ ` limit: 10,`,
3153
+ ` sort: '-createdAt'`,
3154
+ `})`,
3155
+ ``,
3156
+ `const item = await client.collections.from('${collection}').findById(id)`,
3157
+ `const { totalDocs } = await client.collections.from('${collection}').count()`
3158
+ );
3159
+ } else {
3160
+ parts.push(
3161
+ `// Server-only collection: use ServerClient`,
3162
+ `const result = await serverClient.collections.from('${collection}').find({`,
3163
+ ` limit: 10,`,
3164
+ ` sort: '-createdAt'`,
3165
+ `})`,
3166
+ ``,
3167
+ `const item = await serverClient.collections.from('${collection}').findById(id)`
3168
+ );
3169
+ }
2781
3170
  }
2782
3171
  if (operation === "write" || operation === "full-crud") {
2783
3172
  parts.push(
@@ -2792,11 +3181,12 @@ function generatePattern(collection, operation, surface) {
2792
3181
  code: parts.join("\n"),
2793
3182
  notes: [
2794
3183
  "Query Builder works with both Client and ServerClient for reads",
3184
+ !isPublicCollection ? "This collection is server-only" : "",
2795
3185
  operation !== "read" ? "Write operations require ServerClient" : ""
2796
3186
  ].filter(Boolean)
2797
3187
  };
2798
3188
  }
2799
- function handler5({
3189
+ function handler6({
2800
3190
  collection,
2801
3191
  operation,
2802
3192
  surface
@@ -2825,13 +3215,13 @@ function handler5({
2825
3215
 
2826
3216
  // src/prompts/sdk-usage-guide.ts
2827
3217
  import { z as z28 } from "zod";
2828
- var schema30 = {
3218
+ var schema31 = {
2829
3219
  goal: z28.string().describe('What the user wants to accomplish (e.g., "query product list", "create order")'),
2830
3220
  runtime: z28.enum(["browser", "server"]).optional().describe("Target runtime: browser (React/Next.js client) or server (Node.js)"),
2831
3221
  surface: z28.enum(["query-builder", "react-query", "customer-api", "server-api"]).optional().describe("Preferred API surface"),
2832
3222
  collection: z28.string().optional().describe("Specific collection if relevant")
2833
3223
  };
2834
- var metadata30 = {
3224
+ var metadata31 = {
2835
3225
  name: "sdk-usage-guide",
2836
3226
  title: "SDK Usage Guide",
2837
3227
  description: "Provides guidance on how to perform a specific task using the 01.software SDK",
@@ -2969,13 +3359,13 @@ You can perform the "${goal}" task by following the patterns above.`;
2969
3359
 
2970
3360
  // src/prompts/collection-query-help.ts
2971
3361
  import { z as z29 } from "zod";
2972
- import { COLLECTIONS as COLLECTIONS5 } from "@01.software/sdk";
2973
- var schema31 = {
2974
- collection: z29.enum(COLLECTIONS5).describe("Collection name"),
3362
+ import { COLLECTIONS as COLLECTIONS2, SERVER_COLLECTIONS as SERVER_COLLECTIONS5 } from "@01.software/sdk";
3363
+ var schema32 = {
3364
+ collection: z29.enum(SERVER_COLLECTIONS5).describe("Collection name"),
2975
3365
  operation: z29.enum(["find", "create", "update", "delete"]).describe("Operation to perform (find, create, update, delete)"),
2976
3366
  filters: z29.string().optional().describe("Filter conditions (JSON string, optional)")
2977
3367
  };
2978
- var metadata31 = {
3368
+ var metadata32 = {
2979
3369
  name: "collection-query-help",
2980
3370
  title: "Collection Query Help",
2981
3371
  description: "Provides guidance on how to write queries for a specific collection",
@@ -2992,6 +3382,11 @@ Filter conditions:
2992
3382
  \`\`\`json
2993
3383
  ${filters}
2994
3384
  \`\`\`` : "";
3385
+ const isPublicCollection = COLLECTIONS2.includes(
3386
+ collection
3387
+ );
3388
+ const readClientName = isPublicCollection ? "client" : "serverClient";
3389
+ const readClientNote = isPublicCollection ? "Client or ServerClient" : "ServerClient only";
2995
3390
  return `How to perform "${operation}" operation on "${collection}" collection:${filterExample}
2996
3391
 
2997
3392
  ## Collection: ${collection}
@@ -3002,26 +3397,26 @@ ${filters}
3002
3397
  \`\`\`typescript
3003
3398
  import { createClient, createServerClient } from '@01.software/sdk'
3004
3399
 
3005
- // Client (read-only)
3400
+ // Client (read-only public collections)
3006
3401
  const client = createClient({
3007
3402
  publishableKey: process.env.NEXT_PUBLIC_SOFTWARE_PUBLISHABLE_KEY!
3008
3403
  })
3009
3404
 
3010
- // Server client (full CRUD)
3405
+ // Server client (server/public collections, full CRUD)
3011
3406
  const serverClient = createServerClient({
3012
3407
  publishableKey: process.env.SOFTWARE_PUBLISHABLE_KEY!,
3013
3408
  secretKey: process.env.SOFTWARE_SECRET_KEY!
3014
3409
  })
3015
3410
 
3016
- ${operation === "find" ? `// Query ${collection} collection with Query Builder
3411
+ ${operation === "find" ? `// Query ${collection} collection with Query Builder (${readClientNote})
3017
3412
  // find() returns PayloadFindResponse with docs array and pagination
3018
- const result = await client.collections.from('${collection}').find(${filters ? `{
3413
+ const result = await ${readClientName}.collections.from('${collection}').find(${filters ? `{
3019
3414
  where: ${filters}
3020
3415
  }` : ""})
3021
3416
  // result.docs - array of items
3022
3417
  // result.totalDocs, result.page, result.totalPages, result.hasNextPage, ...
3023
3418
 
3024
- // Using React Hook
3419
+ ${isPublicCollection ? `// Using React Hook
3025
3420
  const { data, isLoading, error } = client.query.useQuery({
3026
3421
  collection: '${collection}',
3027
3422
  options: { limit: 10 }
@@ -3031,19 +3426,19 @@ const { data, isLoading, error } = client.query.useQuery({
3031
3426
  const { data } = client.query.useSuspenseQuery({
3032
3427
  collection: '${collection}',
3033
3428
  options: { limit: 10 }
3034
- })` : operation === "create" ? `// Create ${collection} item (ServerClient only)
3429
+ })` : `// React hooks are browser/public only and do not support '${collection}'.`}` : operation === "create" ? `// Create ${collection} item (ServerClient only)
3035
3430
  // create() returns PayloadMutationResponse with doc and message
3036
- const result = await serverClient.from('${collection}').create({
3431
+ const result = await serverClient.collections.from('${collection}').create({
3037
3432
  // Enter fields
3038
3433
  })
3039
3434
  // result.doc - created item, result.message` : operation === "update" ? `// Update ${collection} item (ServerClient only)
3040
3435
  // update() returns PayloadMutationResponse with doc and message
3041
- const result = await serverClient.from('${collection}').update(id, {
3436
+ const result = await serverClient.collections.from('${collection}').update(id, {
3042
3437
  // Fields to update
3043
3438
  })
3044
3439
  // result.doc - updated item, result.message` : `// Delete ${collection} item (ServerClient only)
3045
3440
  // remove() returns the deleted document directly
3046
- await serverClient.from('${collection}').remove(id)`}
3441
+ await serverClient.collections.from('${collection}').remove(id)`}
3047
3442
  \`\`\`
3048
3443
 
3049
3444
  ### Useful Tips
@@ -3051,7 +3446,7 @@ await serverClient.from('${collection}').remove(id)`}
3051
3446
  ${operation === "find" ? `- Use \`where\` option for filtering (Payload query syntax)
3052
3447
  - Use \`limit\` and \`page\` for pagination
3053
3448
  - Use \`sort\` for sorting (prefix with "-" for descending)
3054
- - React Query hooks: useQuery, useSuspenseQuery, useInfiniteQuery
3449
+ - ${isPublicCollection ? "React Query hooks: useQuery, useSuspenseQuery, useInfiniteQuery" : "React Query hooks are browser/public only; use ServerClient for this collection"}
3055
3450
  - Cache utilities: invalidateQueries, prefetchQuery, getQueryData, setQueryData` : operation === "create" ? `- Requires ServerClient with secretKey
3056
3451
  - Check required fields
3057
3452
  - TypeScript recommended for type safety` : operation === "update" ? `- Requires ServerClient with secretKey
@@ -3063,7 +3458,7 @@ ${operation === "find" ? `- Use \`where\` option for filtering (Payload query sy
3063
3458
 
3064
3459
  // src/prompts/order-flow-guide.ts
3065
3460
  import { z as z30 } from "zod";
3066
- var schema32 = {
3461
+ var schema33 = {
3067
3462
  scenario: z30.enum([
3068
3463
  "simple-order",
3069
3464
  "cart-checkout",
@@ -3071,7 +3466,7 @@ var schema32 = {
3071
3466
  "fulfillment-tracking"
3072
3467
  ]).describe("Order flow scenario")
3073
3468
  };
3074
- var metadata32 = {
3469
+ var metadata33 = {
3075
3470
  name: "order-flow-guide",
3076
3471
  title: "Order Flow Guide",
3077
3472
  description: "Provides step-by-step guidance for ecommerce order flows including creation, checkout, returns, and fulfillment.",
@@ -3257,7 +3652,7 @@ ${SCENARIOS[scenario] || "Unknown scenario."}
3257
3652
 
3258
3653
  // src/prompts/feature-setup-guide.ts
3259
3654
  import { z as z31 } from "zod";
3260
- var schema33 = {
3655
+ var schema34 = {
3261
3656
  feature: z31.enum([
3262
3657
  "ecommerce",
3263
3658
  "customers",
@@ -3273,10 +3668,10 @@ var schema33 = {
3273
3668
  "community"
3274
3669
  ]).describe("Feature to get setup guide for")
3275
3670
  };
3276
- var metadata33 = {
3671
+ var metadata34 = {
3277
3672
  name: "feature-setup-guide",
3278
3673
  title: "Feature Setup Guide",
3279
- description: "Setup checklist and remediation guide for a tenant feature. Load before using get-tenant-context to diagnose setup gaps.",
3674
+ description: "Setup checklist and remediation guide for a tenant feature. Load with check-feature-progress and get-tenant-context to diagnose setup gaps.",
3280
3675
  role: "assistant"
3281
3676
  };
3282
3677
  var FEATURES = {
@@ -3287,7 +3682,7 @@ var FEATURES = {
3287
3682
  ### Required Collections (count > 0)
3288
3683
 
3289
3684
  1. **products** \u2014 Create via Console UI or SDK \`client.collections.from('products').create({ ... })\`
3290
- - Minimum fields: \`{ title, slug, status: 'published', _status: 'published' }\`
3685
+ - Minimum fields: \`{ title, slug, status: 'published' }\`
3291
3686
 
3292
3687
  2. **product-variants** \u2014 At least 1 sellable variant per product
3293
3688
  - Minimum fields: \`{ product, title, price, stock }\`
@@ -3306,6 +3701,7 @@ product-options, product-option-values, product-categories, product-tags, produc
3306
3701
  ### Config
3307
3702
 
3308
3703
  - **Webhook URL** must be configured in tenant settings for payment gateway callbacks
3704
+ - Use \`check-feature-progress\` for the tenant-aware ecommerce progress check
3309
3705
  - Use \`get-tenant-context\` to check current webhook configuration`,
3310
3706
  customers: `## Customers Setup Guide
3311
3707
 
@@ -3320,7 +3716,8 @@ customer-addresses
3320
3716
 
3321
3717
  ### Optional Collections
3322
3718
 
3323
- customer-groups \u2014 Create via Console UI or SDK \`client.collections.from('customer-groups').create({ title })\`
3719
+ - customer-groups \u2014 Console/server-scoped segmentation for VIP coupons and campaigns. Use \`createServerClient().collections.from('customer-groups')\`.
3720
+ - customer-profile-lists \u2014 Public profile display/ranking lists for storefronts. Browser reads may use \`client.collections.from('customer-profile-lists')\`.
3324
3721
 
3325
3722
  ### Config
3326
3723
 
@@ -3331,10 +3728,10 @@ customer-groups \u2014 Create via Console UI or SDK \`client.collections.from('c
3331
3728
  ### Required Collections (count > 0)
3332
3729
 
3333
3730
  1. **articles** \u2014 At least 1 article
3334
- - Minimum fields: \`{ title, slug }\`
3731
+ - Minimum fields: \`{ title, slug, status: 'published' }\`
3335
3732
 
3336
3733
  2. **article-authors** \u2014 At least 1 author
3337
- - Minimum fields: \`{ title, slug }\`
3734
+ - Minimum fields: \`{ title, slug, status: 'published' }\`
3338
3735
  - Link authors to articles via the \`authors\` relationship field
3339
3736
 
3340
3737
  ### Optional Collections
@@ -3349,7 +3746,7 @@ article-categories, article-tags`,
3349
3746
 
3350
3747
  2. **document-types** \u2014 At least 1 type
3351
3748
  - Minimum fields: \`{ title, slug }\`
3352
- - Link document type via \`documentType\` relationship field
3749
+ - Link document type via \`type\` relationship field
3353
3750
 
3354
3751
  ### Optional Collections
3355
3752
 
@@ -3359,10 +3756,10 @@ document-categories`,
3359
3756
  ### Required Collections (count > 0)
3360
3757
 
3361
3758
  1. **playlists** \u2014 At least 1 playlist
3362
- - Minimum fields: \`{ title, slug, status: 'published', _status: 'published' }\`
3759
+ - Minimum fields: \`{ title, slug, status: 'published' }\`
3363
3760
 
3364
3761
  2. **tracks** \u2014 At least 1 track
3365
- - Minimum fields: \`{ title, sourceUrl, status: 'published', _status: 'published' }\`
3762
+ - Minimum fields: \`{ title, sourceUrl, status: 'published' }\`
3366
3763
 
3367
3764
  3. **playlists.tracks** \u2014 Link at least 1 track from a playlist
3368
3765
  - Minimum fields: \`{ tracks: [trackId] }\`
@@ -3375,11 +3772,11 @@ playlist-categories, playlist-tags, track-categories, track-tags, track-assets`,
3375
3772
  ### Required Collections (count > 0)
3376
3773
 
3377
3774
  1. **galleries** \u2014 At least 1 gallery
3378
- - Minimum fields: \`{ title, slug, status: 'published', _status: 'published' }\`
3775
+ - Minimum fields: \`{ title, slug, status: 'published' }\`
3379
3776
 
3380
3777
  2. **gallery-items** \u2014 At least 1 item per gallery
3381
3778
  - References \`images\` collection (non-upload)
3382
- - Minimum fields: \`{ gallery, image, _status: 'published' }\`
3779
+ - Minimum fields: \`{ gallery, image, status: 'published' }\`
3383
3780
 
3384
3781
  ### Optional Collections
3385
3782
 
@@ -3389,7 +3786,7 @@ gallery-categories, gallery-tags`,
3389
3786
  ### Required Collections (count > 0)
3390
3787
 
3391
3788
  1. **links** \u2014 At least 1 link
3392
- - Minimum fields: \`{ title, slug, url, status: 'published', _status: 'published' }\`
3789
+ - Minimum fields: \`{ title, slug, url, status: 'published' }\`
3393
3790
 
3394
3791
  ### Optional Collections
3395
3792
 
@@ -3461,32 +3858,36 @@ comments, reactions, bookmarks, reports, community-bans
3461
3858
 
3462
3859
  ### Optional Collections
3463
3860
 
3464
- post-categories`
3861
+ post-categories, customer-profile-lists`
3465
3862
  };
3466
- function featureSetupGuide({ feature }) {
3863
+ function featureSetupGuide({
3864
+ feature
3865
+ }) {
3467
3866
  return `# Feature Setup Guide: ${feature}
3468
3867
 
3469
3868
  ${FEATURES[feature] || "Unknown feature."}
3470
3869
 
3471
3870
  ## Related MCP Tools
3871
+ - \`check-feature-progress\` \u2014 run the tenant-aware ecommerce implementation progress check
3472
3872
  - \`get-tenant-context\` \u2014 check current collection counts and feature status
3473
3873
  - \`query-collection\` \u2014 verify existing documents in a collection
3474
3874
  - \`get-collection-schema\` \u2014 inspect tenant-aware fields before creating data via SDK or Console UI`;
3475
3875
  }
3476
3876
 
3477
3877
  // src/resources/(config)/app.ts
3478
- var metadata34 = {
3878
+ var metadata35 = {
3479
3879
  name: "app-config",
3480
3880
  title: "Application Config",
3481
3881
  description: "01.software SDK and MCP server configuration information"
3482
3882
  };
3483
- function handler6() {
3883
+ function handler7() {
3484
3884
  return `# 01.software MCP Server Configuration
3485
3885
 
3486
3886
  ## Server Info
3487
3887
  - **Name**: 01.software MCP Server
3488
3888
  - **Version**: 0.1.0
3489
- - **Transport**: HTTP (Streamable)
3889
+ - **Hosted transport**: HTTP (Streamable)
3890
+ - **Local transport**: stdio through \`npx @01.software/cli mcp\`
3490
3891
 
3491
3892
  ## Authentication
3492
3893
 
@@ -3497,48 +3898,16 @@ HTTP MCP uses OAuth discovery and Authorization Code + PKCE.
3497
3898
  url = "https://mcp.01.software/mcp"
3498
3899
  \`\`\`
3499
3900
 
3500
- ## Available Tools (29)
3501
-
3502
- > Generic write tools (create/update/delete/update-many/delete-many) are intentionally absent. Use the dedicated workflow tools below or the SDK (\`client.collections.from(slug).create()\` / \`update()\` / \`remove()\` / \`updateMany()\` / \`removeMany()\`) for stateful mutations.
3503
-
3504
- ### Generic Read (2)
3505
- - \`query-collection\` - Query collection with filters, pagination, sorting
3506
- - \`get-collection-by-id\` - Get single item by ID
3507
-
3508
- ### Orders (7)
3509
- - \`create-order\` - Create a new order with products and shipping
3510
- - \`get-order\` - Get order details by order number
3511
- - \`update-order\` - Update order status
3512
- - \`checkout\` - Convert cart to order
3513
- - \`create-fulfillment\` - Create fulfillment for order items
3514
- - \`update-fulfillment\` - Update fulfillment status, carrier, and tracking
3515
- - \`update-transaction\` - Update transaction status
3901
+ ## Hosted HTTP OAuth Tools (9)
3516
3902
 
3517
- ### Returns (3)
3518
- - \`create-return\` - Create a return request
3519
- - \`update-return\` - Update return status
3520
- - \`return-with-refund\` - Process return with refund atomically
3521
-
3522
- ### Cart (6)
3523
- - \`add-cart-item\` - Add item to cart
3524
- - \`update-cart-item\` - Update cart item quantity
3525
- - \`remove-cart-item\` - Remove item from cart
3526
- - \`apply-discount\` - Apply discount code to cart
3527
- - \`remove-discount\` - Remove discount from cart
3528
- - \`clear-cart\` - Remove all items from cart
3529
-
3530
- ### Validation (2)
3531
- - \`validate-discount\` - Validate discount code
3532
- - \`calculate-shipping\` - Calculate shipping fee
3533
-
3534
- ### Product (1)
3535
- - \`stock-check\` - Check product option stock availability
3903
+ The hosted HTTP MCP endpoint at https://mcp.01.software/mcp exposes only these OAuth-safe tools:
3536
3904
 
3537
3905
  ### Schema (1)
3538
3906
  - \`get-collection-schema\` - Get authoritative tenant-aware collection schema
3539
3907
 
3540
- ### Tenant Context (1)
3908
+ ### Tenant Context (2)
3541
3909
  - \`get-tenant-context\` - Get tenant features, active collections, and field config
3910
+ - \`check-feature-progress\` - Check ecommerce implementation progress without mutating tenant data
3542
3911
 
3543
3912
  ### Field Config (2)
3544
3913
  - \`list-configurable-fields\` - List configurable fields and current hidden state
@@ -3550,6 +3919,16 @@ url = "https://mcp.01.software/mcp"
3550
3919
  - \`sdk-get-auth-setup\` - Get framework-specific auth setup guidance
3551
3920
  - \`sdk-get-collection-pattern\` - Get collection-specific usage patterns
3552
3921
 
3922
+ ## Local CLI Stdio Surface (30)
3923
+
3924
+ For trusted local server-key workflows, start the stdio server:
3925
+
3926
+ \`\`\`bash
3927
+ npx @01.software/cli mcp
3928
+ \`\`\`
3929
+
3930
+ Local stdio can expose generic read, order, return, cart, validation, stock, schema, tenant context, feature progress, field config, and guidance tools. Generic collection write tools (create/update/delete/update-many/delete-many) are intentionally absent on every transport; use the SDK server client for generic writes.
3931
+
3553
3932
  ## Rate Limits
3554
3933
 
3555
3934
  Rate limits depend on your tenant plan:
@@ -3561,8 +3940,8 @@ Rate limits depend on your tenant plan:
3561
3940
  }
3562
3941
 
3563
3942
  // src/resources/(collections)/schema.ts
3564
- import { COLLECTIONS as COLLECTIONS6 } from "@01.software/sdk";
3565
- var metadata35 = {
3943
+ import { COLLECTIONS as COLLECTIONS3 } from "@01.software/sdk";
3944
+ var metadata36 = {
3566
3945
  name: "collections-schema",
3567
3946
  title: "Collection Schema Info",
3568
3947
  description: "Available collections and their schema information"
@@ -3590,13 +3969,18 @@ var COLLECTIONS_BY_CATEGORY = {
3590
3969
  Customers: [
3591
3970
  "customers",
3592
3971
  "customer-profiles",
3593
- "customer-addresses",
3594
- "customer-groups"
3972
+ "customer-profile-lists",
3973
+ "customer-addresses"
3595
3974
  ],
3596
3975
  Carts: ["carts", "cart-items"],
3597
3976
  "Discounts & Promotions": ["discounts", "promotions"],
3598
3977
  Documents: ["documents", "document-categories", "document-types"],
3599
- Articles: ["articles", "article-authors", "article-categories", "article-tags"],
3978
+ Articles: [
3979
+ "articles",
3980
+ "article-authors",
3981
+ "article-categories",
3982
+ "article-tags"
3983
+ ],
3600
3984
  Community: [
3601
3985
  "posts",
3602
3986
  "comments",
@@ -3615,7 +3999,12 @@ var COLLECTIONS_BY_CATEGORY = {
3615
3999
  "track-categories",
3616
4000
  "track-tags"
3617
4001
  ],
3618
- Galleries: ["galleries", "gallery-items", "gallery-categories", "gallery-tags"],
4002
+ Galleries: [
4003
+ "galleries",
4004
+ "gallery-items",
4005
+ "gallery-categories",
4006
+ "gallery-tags"
4007
+ ],
3619
4008
  Links: ["links", "link-categories", "link-tags"],
3620
4009
  Canvas: [
3621
4010
  "canvases",
@@ -3638,9 +4027,9 @@ var COLLECTIONS_BY_CATEGORY = {
3638
4027
  "event-tags"
3639
4028
  ]
3640
4029
  };
3641
- function handler7() {
4030
+ function handler8() {
3642
4031
  const categoryDocs = Object.entries(COLLECTIONS_BY_CATEGORY).map(([category, collections]) => {
3643
- const collectionList = collections.filter((c) => COLLECTIONS6.includes(c)).map((c) => `- **${c}**`).join("\n");
4032
+ const collectionList = collections.filter((c) => COLLECTIONS3.includes(c)).map((c) => `- **${c}**`).join("\n");
3644
4033
  return `## ${category}
3645
4034
  ${collectionList}`;
3646
4035
  }).join("\n\n");
@@ -3661,8 +4050,9 @@ Each collection supports the following operations:
3661
4050
  - \`updateMany(where, data)\` - Bulk update items matching filter
3662
4051
  - \`removeMany(where)\` - Bulk delete items matching filter
3663
4052
 
3664
- Draft-enabled public collections expose only \`_status: 'published'\` rows to
3665
- publishable-key reads unless server-side access explicitly includes drafts.
4053
+ Status-managed public collections expose only \`status: 'published'\` rows to
4054
+ publishable-key reads unless server-side access explicitly includes
4055
+ unpublished statuses.
3666
4056
 
3667
4057
  ## Query Examples
3668
4058
 
@@ -3685,16 +4075,16 @@ publishable-key reads unless server-side access explicitly includes drafts.
3685
4075
  }
3686
4076
  \`\`\`
3687
4077
 
3688
- Total available collections: ${COLLECTIONS6.length}`;
4078
+ Total available collections: ${COLLECTIONS3.length}`;
3689
4079
  }
3690
4080
 
3691
4081
  // src/resources/(docs)/getting-started.ts
3692
- var metadata36 = {
4082
+ var metadata37 = {
3693
4083
  name: "docs-getting-started",
3694
4084
  title: "Getting Started",
3695
4085
  description: "01.software SDK getting started guide"
3696
4086
  };
3697
- function handler8() {
4087
+ function handler9() {
3698
4088
  return `# Getting Started
3699
4089
 
3700
4090
  A guide to getting started with the 01.software SDK.
@@ -3728,18 +4118,18 @@ const result = await client.collections.from('products').find({
3728
4118
 
3729
4119
  ## Next Steps
3730
4120
 
3731
- - [Quick Start](/docs/getting-started/quick-start) - Get started in 5 minutes
3732
- - [Configuration](/docs/getting-started/configuration) - Detailed configuration options
3733
- - [API Reference](/docs/api) - Full API documentation`;
4121
+ - [SDK Guide](/developers/sdk) - Install and query workspace content
4122
+ - [Authentication & Keys](/developers/authentication) - Choose the right key for each surface
4123
+ - [API](/developers/api) - Use the HTTP API when SDKs are not a fit`;
3734
4124
  }
3735
4125
 
3736
4126
  // src/resources/(docs)/guides.ts
3737
- var metadata37 = {
4127
+ var metadata38 = {
3738
4128
  name: "docs-guides",
3739
4129
  title: "Guides",
3740
4130
  description: "01.software SDK usage guides"
3741
4131
  };
3742
- function handler9() {
4132
+ function handler10() {
3743
4133
  return `# Guides
3744
4134
 
3745
4135
  Comprehensive guides to master the 01.software SDK.
@@ -3941,16 +4331,16 @@ Payload query syntax operators:
3941
4331
 
3942
4332
  For ecommerce collections, \`products.listing.*\` is the browse/search projection. Authoritative sellable price and stock remain on \`product-variants\`.
3943
4333
 
3944
- For more detailed guides, see the [Guides page](/docs/guides).`;
4334
+ For more implementation guidance, see the [SDK Guide](/developers/sdk).`;
3945
4335
  }
3946
4336
 
3947
4337
  // src/resources/(docs)/api.ts
3948
- var metadata38 = {
4338
+ var metadata39 = {
3949
4339
  name: "docs-api",
3950
4340
  title: "API Reference",
3951
4341
  description: "01.software SDK API reference documentation"
3952
4342
  };
3953
- function handler10() {
4343
+ function handler11() {
3954
4344
  return `# API Reference
3955
4345
 
3956
4346
  Comprehensive documentation for all methods and types in the 01.software SDK.
@@ -4227,16 +4617,16 @@ client.customer.isAuthenticated() // Check auth status
4227
4617
  client.customer.logout() // Clear token
4228
4618
  \`\`\`
4229
4619
 
4230
- For more details, see the [full API documentation](/docs/api).`;
4620
+ For more details, see the [API documentation](/developers/api).`;
4231
4621
  }
4232
4622
 
4233
4623
  // src/resources/(docs)/query-builder.ts
4234
- var metadata39 = {
4624
+ var metadata40 = {
4235
4625
  name: "docs-query-builder",
4236
4626
  title: "Query Builder",
4237
4627
  description: "01.software SDK Query Builder API reference (client.collections.from)"
4238
4628
  };
4239
- function handler11() {
4629
+ function handler12() {
4240
4630
  return `# Query Builder API
4241
4631
 
4242
4632
  The Query Builder provides a fluent interface for querying collections via \`client.collections.from(collection)\`.
@@ -4425,12 +4815,12 @@ console.log(result.hasNextPage) // true
4425
4815
  }
4426
4816
 
4427
4817
  // src/resources/(docs)/react-query.ts
4428
- var metadata40 = {
4818
+ var metadata41 = {
4429
4819
  name: "docs-react-query",
4430
4820
  title: "React Query Hooks",
4431
4821
  description: "01.software SDK React Query hooks reference (client.query)"
4432
4822
  };
4433
- function handler12() {
4823
+ function handler13() {
4434
4824
  return `# React Query Hooks
4435
4825
 
4436
4826
  React Query hooks are available on the browser-side \`Client\` via \`client.query\`. They provide automatic caching, background refetching, and cache invalidation.
@@ -4673,12 +5063,12 @@ export function ProductList() {
4673
5063
  }
4674
5064
 
4675
5065
  // src/resources/(docs)/server-api.ts
4676
- var metadata41 = {
5066
+ var metadata42 = {
4677
5067
  name: "docs-server-api",
4678
5068
  title: "Server-side API",
4679
5069
  description: "01.software SDK server-side API reference (client.commerce) for orders, fulfillments, returns, carts, and validation"
4680
5070
  };
4681
- function handler13() {
5071
+ function handler14() {
4682
5072
  return `# Server-side API
4683
5073
 
4684
5074
  Server-side operations are available via \`client.commerce\` on \`ServerClient\`. Use \`createServerClient\` with both \`publishableKey\` and \`secretKey\`.
@@ -4935,12 +5325,12 @@ const result = await client.commerce.shipping.calculate({
4935
5325
  }
4936
5326
 
4937
5327
  // src/resources/(docs)/customer-auth.ts
4938
- var metadata42 = {
5328
+ var metadata43 = {
4939
5329
  name: "docs-customer-auth",
4940
5330
  title: "Customer Auth API",
4941
5331
  description: "01.software SDK Customer Auth API reference (client.customer)"
4942
5332
  };
4943
- function handler14() {
5333
+ function handler15() {
4944
5334
  return `# Customer Auth API
4945
5335
 
4946
5336
  Customer authentication and profile management is available via \`client.customer\` on the browser-side \`Client\`.
@@ -5113,12 +5503,12 @@ async function loadProfile() {
5113
5503
  }
5114
5504
 
5115
5505
  // src/resources/(docs)/browser-vs-server.ts
5116
- var metadata43 = {
5506
+ var metadata44 = {
5117
5507
  name: "docs-browser-vs-server",
5118
5508
  title: "Client vs ServerClient",
5119
5509
  description: "When to use Client (createClient) vs ServerClient (createServerClient) in the 01.software SDK"
5120
5510
  };
5121
- function handler15() {
5511
+ function handler16() {
5122
5512
  return `# Client vs ServerClient
5123
5513
 
5124
5514
  The SDK provides two client types for different execution environments.
@@ -5272,12 +5662,12 @@ export function ProductList() {
5272
5662
  }
5273
5663
 
5274
5664
  // src/resources/(docs)/file-upload.ts
5275
- var metadata44 = {
5665
+ var metadata45 = {
5276
5666
  name: "docs-file-upload",
5277
5667
  title: "File Upload",
5278
5668
  description: "01.software SDK file upload patterns using the images collection"
5279
5669
  };
5280
- function handler16() {
5670
+ function handler17() {
5281
5671
  return `# File Upload
5282
5672
 
5283
5673
  Upload files using the \`images\` collection (tenant-scoped, unified image store) or \`system-media\` (global, non-tenant).
@@ -5423,12 +5813,12 @@ The platform stores files in Cloudflare R2 and serves via CDN (\`cdn.01.software
5423
5813
  }
5424
5814
 
5425
5815
  // src/resources/(docs)/webhook.ts
5426
- var metadata45 = {
5816
+ var metadata46 = {
5427
5817
  name: "docs-webhook",
5428
5818
  title: "Webhooks",
5429
5819
  description: "01.software SDK webhook verification and event handling"
5430
5820
  };
5431
- function handler17() {
5821
+ function handler18() {
5432
5822
  return `# Webhooks
5433
5823
 
5434
5824
  The platform dispatches HMAC-SHA256 signed webhook events to your registered URLs. Tenant developers own routing inside their webhook handler.
@@ -5538,7 +5928,7 @@ Configure webhook URLs in the 01.software console under Tenant Settings > Webhoo
5538
5928
 
5539
5929
  // src/server.ts
5540
5930
  var REGISTERED_TOOLS_BY_SERVER = /* @__PURE__ */ new WeakMap();
5541
- function registerTool(server, schema34, meta, handler18) {
5931
+ function registerTool(server, schema35, meta, handler19) {
5542
5932
  let registered = REGISTERED_TOOLS_BY_SERVER.get(server);
5543
5933
  if (!registered) {
5544
5934
  registered = /* @__PURE__ */ new Set();
@@ -5549,7 +5939,7 @@ function registerTool(server, schema34, meta, handler18) {
5549
5939
  meta.name,
5550
5940
  {
5551
5941
  description: meta.description,
5552
- inputSchema: schema34,
5942
+ inputSchema: schema35,
5553
5943
  annotations: meta.annotations
5554
5944
  },
5555
5945
  // eslint-disable-next-line @typescript-eslint/no-explicit-any
@@ -5573,31 +5963,48 @@ function registerTool(server, schema34, meta, handler18) {
5573
5963
  };
5574
5964
  }
5575
5965
  }
5576
- const result = await handler18(params);
5577
- return { content: [{ type: "text", text: result }] };
5966
+ const activeSummary = currentMcpTelemetrySummary();
5967
+ const ownSummary = activeSummary || hasRequestContext() ? null : createMcpTelemetrySummary("stdio");
5968
+ const summary = activeSummary ?? ownSummary;
5969
+ let result = null;
5970
+ try {
5971
+ result = await handler19(params);
5972
+ return { content: [{ type: "text", text: result }] };
5973
+ } finally {
5974
+ if (summary) {
5975
+ recordMcpToolResult({
5976
+ resultText: result,
5977
+ summary,
5978
+ toolName: meta.name
5979
+ });
5980
+ }
5981
+ if (ownSummary) {
5982
+ void flushMcpTelemetrySummary(ownSummary);
5983
+ }
5984
+ }
5578
5985
  }
5579
5986
  );
5580
5987
  }
5581
- function registerPrompt(server, schema34, meta, handler18) {
5988
+ function registerPrompt(server, schema35, meta, handler19) {
5582
5989
  server.registerPrompt(
5583
5990
  meta.name,
5584
5991
  {
5585
5992
  title: meta.title,
5586
5993
  description: meta.description,
5587
- argsSchema: schema34
5994
+ argsSchema: schema35
5588
5995
  },
5589
5996
  // eslint-disable-next-line @typescript-eslint/no-explicit-any
5590
5997
  (params) => ({
5591
5998
  messages: [
5592
5999
  {
5593
6000
  role: meta.role ?? "assistant",
5594
- content: { type: "text", text: handler18(params) }
6001
+ content: { type: "text", text: handler19(params) }
5595
6002
  }
5596
6003
  ]
5597
6004
  })
5598
6005
  );
5599
6006
  }
5600
- function registerStaticResource(server, uri, meta, handler18) {
6007
+ function registerStaticResource(server, uri, meta, handler19) {
5601
6008
  server.registerResource(
5602
6009
  meta.name,
5603
6010
  uri,
@@ -5607,7 +6014,7 @@ function registerStaticResource(server, uri, meta, handler18) {
5607
6014
  mimeType: meta.mimeType ?? "text/plain"
5608
6015
  },
5609
6016
  async (url) => ({
5610
- contents: [{ uri: url.href, text: handler18() }]
6017
+ contents: [{ uri: url.href, text: handler19() }]
5611
6018
  })
5612
6019
  );
5613
6020
  }
@@ -5618,52 +6025,238 @@ function createServer(options = {}) {
5618
6025
  version: "0.1.0"
5619
6026
  });
5620
6027
  if (toolSurface === "full") {
5621
- registerTool(server, schema, metadata, queryCollection);
5622
- registerTool(server, schema2, metadata2, getCollectionById);
6028
+ registerTool(
6029
+ server,
6030
+ schema,
6031
+ metadata,
6032
+ queryCollection
6033
+ );
6034
+ registerTool(
6035
+ server,
6036
+ schema2,
6037
+ metadata2,
6038
+ getCollectionById
6039
+ );
5623
6040
  registerTool(server, schema3, metadata3, getOrder);
5624
6041
  registerTool(server, schema4, metadata4, createOrder);
5625
6042
  registerTool(server, schema5, metadata5, updateOrder);
5626
6043
  registerTool(server, schema6, metadata6, checkout);
5627
- registerTool(server, schema7, metadata7, createFulfillment);
5628
- registerTool(server, schema8, metadata8, updateFulfillment);
5629
- registerTool(server, schema9, metadata9, updateTransaction);
5630
- registerTool(server, schema10, metadata10, createReturn);
5631
- registerTool(server, schema11, metadata11, updateReturn);
5632
- registerTool(server, schema12, metadata12, returnWithRefund);
6044
+ registerTool(
6045
+ server,
6046
+ schema7,
6047
+ metadata7,
6048
+ createFulfillment
6049
+ );
6050
+ registerTool(
6051
+ server,
6052
+ schema8,
6053
+ metadata8,
6054
+ updateFulfillment
6055
+ );
6056
+ registerTool(
6057
+ server,
6058
+ schema9,
6059
+ metadata9,
6060
+ updateTransaction
6061
+ );
6062
+ registerTool(
6063
+ server,
6064
+ schema10,
6065
+ metadata10,
6066
+ createReturn
6067
+ );
6068
+ registerTool(
6069
+ server,
6070
+ schema11,
6071
+ metadata11,
6072
+ updateReturn
6073
+ );
6074
+ registerTool(
6075
+ server,
6076
+ schema12,
6077
+ metadata12,
6078
+ returnWithRefund
6079
+ );
5633
6080
  registerTool(server, schema13, metadata13, addCartItem);
5634
- registerTool(server, schema14, metadata14, updateCartItem);
5635
- registerTool(server, schema15, metadata15, removeCartItem);
5636
- registerTool(server, schema16, metadata16, applyDiscount);
5637
- registerTool(server, schema17, metadata17, removeDiscount);
6081
+ registerTool(
6082
+ server,
6083
+ schema14,
6084
+ metadata14,
6085
+ updateCartItem
6086
+ );
6087
+ registerTool(
6088
+ server,
6089
+ schema15,
6090
+ metadata15,
6091
+ removeCartItem
6092
+ );
6093
+ registerTool(
6094
+ server,
6095
+ schema16,
6096
+ metadata16,
6097
+ applyDiscount
6098
+ );
6099
+ registerTool(
6100
+ server,
6101
+ schema17,
6102
+ metadata17,
6103
+ removeDiscount
6104
+ );
5638
6105
  registerTool(server, schema18, metadata18, clearCart);
5639
- registerTool(server, schema19, metadata19, validateDiscount);
5640
- registerTool(server, schema20, metadata20, calculateShipping);
6106
+ registerTool(
6107
+ server,
6108
+ schema19,
6109
+ metadata19,
6110
+ validateDiscount
6111
+ );
6112
+ registerTool(
6113
+ server,
6114
+ schema20,
6115
+ metadata20,
6116
+ calculateShipping
6117
+ );
5641
6118
  registerTool(server, schema21, metadata21, stockCheck);
5642
6119
  }
5643
- registerTool(server, schema22, metadata22, getCollectionSchemaTool);
5644
- registerTool(server, schema23, metadata23, handler);
5645
- registerTool(server, schema24, metadata24, listConfigurableFields);
5646
- registerTool(server, schema25, metadata25, updateFieldConfig);
5647
- registerTool(server, schema26, metadata26, handler2);
5648
- registerTool(server, schema27, metadata27, handler3);
5649
- registerTool(server, schema28, metadata28, handler4);
5650
- registerTool(server, schema29, metadata29, handler5);
5651
- registerPrompt(server, schema30, metadata30, sdkUsageGuide);
5652
- registerPrompt(server, schema31, metadata31, collectionQueryHelp);
5653
- registerPrompt(server, schema32, metadata32, orderFlowGuide);
5654
- registerPrompt(server, schema33, metadata33, featureSetupGuide);
5655
- registerStaticResource(server, "config://app", metadata34, handler6);
5656
- registerStaticResource(server, "collections://schema", metadata35, handler7);
5657
- registerStaticResource(server, "docs://sdk/getting-started", metadata36, handler8);
5658
- registerStaticResource(server, "docs://sdk/guides", metadata37, handler9);
5659
- registerStaticResource(server, "docs://sdk/api", metadata38, handler10);
5660
- registerStaticResource(server, "docs://sdk/query-builder", metadata39, handler11);
5661
- registerStaticResource(server, "docs://sdk/react-query", metadata40, handler12);
5662
- registerStaticResource(server, "docs://sdk/server-api", metadata41, handler13);
5663
- registerStaticResource(server, "docs://sdk/customer-auth", metadata42, handler14);
5664
- registerStaticResource(server, "docs://sdk/browser-vs-server", metadata43, handler15);
5665
- registerStaticResource(server, "docs://sdk/file-upload", metadata44, handler16);
5666
- registerStaticResource(server, "docs://sdk/webhook", metadata45, handler17);
6120
+ registerTool(
6121
+ server,
6122
+ schema22,
6123
+ metadata22,
6124
+ getCollectionSchemaTool
6125
+ );
6126
+ registerTool(
6127
+ server,
6128
+ schema23,
6129
+ metadata23,
6130
+ handler
6131
+ );
6132
+ registerTool(
6133
+ server,
6134
+ schema24,
6135
+ metadata24,
6136
+ handler2
6137
+ );
6138
+ registerTool(
6139
+ server,
6140
+ schema25,
6141
+ metadata25,
6142
+ listConfigurableFields
6143
+ );
6144
+ registerTool(
6145
+ server,
6146
+ schema26,
6147
+ metadata26,
6148
+ updateFieldConfig
6149
+ );
6150
+ registerTool(
6151
+ server,
6152
+ schema27,
6153
+ metadata27,
6154
+ handler3
6155
+ );
6156
+ registerTool(
6157
+ server,
6158
+ schema28,
6159
+ metadata28,
6160
+ handler4
6161
+ );
6162
+ registerTool(
6163
+ server,
6164
+ schema29,
6165
+ metadata29,
6166
+ handler5
6167
+ );
6168
+ registerTool(
6169
+ server,
6170
+ schema30,
6171
+ metadata30,
6172
+ handler6
6173
+ );
6174
+ registerPrompt(
6175
+ server,
6176
+ schema31,
6177
+ metadata31,
6178
+ sdkUsageGuide
6179
+ );
6180
+ registerPrompt(
6181
+ server,
6182
+ schema32,
6183
+ metadata32,
6184
+ collectionQueryHelp
6185
+ );
6186
+ registerPrompt(
6187
+ server,
6188
+ schema33,
6189
+ metadata33,
6190
+ orderFlowGuide
6191
+ );
6192
+ registerPrompt(
6193
+ server,
6194
+ schema34,
6195
+ metadata34,
6196
+ featureSetupGuide
6197
+ );
6198
+ registerStaticResource(
6199
+ server,
6200
+ "config://app",
6201
+ metadata35,
6202
+ handler7
6203
+ );
6204
+ registerStaticResource(
6205
+ server,
6206
+ "collections://schema",
6207
+ metadata36,
6208
+ handler8
6209
+ );
6210
+ registerStaticResource(
6211
+ server,
6212
+ "docs://sdk/getting-started",
6213
+ metadata37,
6214
+ handler9
6215
+ );
6216
+ registerStaticResource(server, "docs://sdk/guides", metadata38, handler10);
6217
+ registerStaticResource(server, "docs://sdk/api", metadata39, handler11);
6218
+ registerStaticResource(
6219
+ server,
6220
+ "docs://sdk/query-builder",
6221
+ metadata40,
6222
+ handler12
6223
+ );
6224
+ registerStaticResource(
6225
+ server,
6226
+ "docs://sdk/react-query",
6227
+ metadata41,
6228
+ handler13
6229
+ );
6230
+ registerStaticResource(
6231
+ server,
6232
+ "docs://sdk/server-api",
6233
+ metadata42,
6234
+ handler14
6235
+ );
6236
+ registerStaticResource(
6237
+ server,
6238
+ "docs://sdk/customer-auth",
6239
+ metadata43,
6240
+ handler15
6241
+ );
6242
+ registerStaticResource(
6243
+ server,
6244
+ "docs://sdk/browser-vs-server",
6245
+ metadata44,
6246
+ handler16
6247
+ );
6248
+ registerStaticResource(
6249
+ server,
6250
+ "docs://sdk/file-upload",
6251
+ metadata45,
6252
+ handler17
6253
+ );
6254
+ registerStaticResource(
6255
+ server,
6256
+ "docs://sdk/webhook",
6257
+ metadata46,
6258
+ handler18
6259
+ );
5667
6260
  return server;
5668
6261
  }
5669
6262
 
@@ -5676,6 +6269,9 @@ export {
5676
6269
  MCP_SCOPES,
5677
6270
  requestContext,
5678
6271
  mcpServicePublicJwks,
6272
+ createMcpTelemetrySummary,
6273
+ runWithMcpTelemetry,
6274
+ flushMcpTelemetrySummary,
5679
6275
  createServer
5680
6276
  };
5681
- //# sourceMappingURL=chunk-GJOQ4SE2.js.map
6277
+ //# sourceMappingURL=chunk-2ECTVUKU.js.map