xytara 1.6.0 → 1.7.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -97,6 +97,14 @@ The next `1.6.0` carry also adds guided default loops on top of those packs:
97
97
 
98
98
  That means the first-party path is easier to both run and inspect without manually stitching together monitor, receipt, delivery, and payment-ledger helpers after execution.
99
99
 
100
+ The current `1.7.0` line starts widening that surface into real grouped transaction classes:
101
+
102
+ - transaction-class pack catalog, summary, and detail routes
103
+ - grouped transaction-class run routes for first-party commerce classes
104
+ - proof-handoff summaries that make the next step into `xoonya` more obvious from transaction outputs
105
+
106
+ This is the first step beyond “clear default loop” toward “broader useful machine-commerce classes plus clearer commerce-to-proof follow-through.”
107
+
100
108
  ## Package Surface
101
109
 
102
110
  The SDK is broad, but it stays organized into a few repeatable families instead of one-off surfaces.
package/index.js CHANGED
@@ -40,7 +40,7 @@ const {
40
40
  } = require("./integrations/registry");
41
41
 
42
42
  const COMMERCE_SDK_NAME = "xytara";
43
- const COMMERCE_SDK_VERSION = "1.6.0";
43
+ const COMMERCE_SDK_VERSION = "1.7.0";
44
44
  const COMMERCE_API_VERSION = "v1";
45
45
 
46
46
  function createClient(options) {
@@ -110,6 +110,83 @@ function buildDefaultTransactionGuidedLoops() {
110
110
  ];
111
111
  }
112
112
 
113
+ function buildTransactionClassPacks() {
114
+ const center = buildDefaultTransactionCenter();
115
+ const defaultSettlementMode = center.default_settlement && center.default_settlement.settlement_mode
116
+ ? center.default_settlement.settlement_mode
117
+ : null;
118
+ const defaultPaymentProtocol = center.default_payment && center.default_payment.protocol
119
+ ? center.default_payment.protocol
120
+ : null;
121
+ return [
122
+ {
123
+ class_pack_ref: "transaction.trust.receipt",
124
+ title: "Trust Receipt Transaction",
125
+ description: "Verify trust posture and validate the paired receipt as one grouped transaction class.",
126
+ workflow_ref: "trust.flow",
127
+ task_refs: ["trust.verify", "receipt.validate"],
128
+ category: "trust",
129
+ proof_handoff_kind: "receipt_validation",
130
+ default_payment_protocol: defaultPaymentProtocol,
131
+ default_settlement_mode: defaultSettlementMode,
132
+ required_inputs: ["subject_id", "receipt_id"],
133
+ optional_inputs: ["payment_protocol", "settlement_mode"]
134
+ },
135
+ {
136
+ class_pack_ref: "transaction.runtime.consequence",
137
+ title: "Runtime Consequence Transaction",
138
+ description: "Emit a runtime consequence and anchor the resulting commitment as one grouped transaction class.",
139
+ workflow_ref: "runtime.consequence.flow",
140
+ task_refs: ["runtime.emit", "runtime.anchor"],
141
+ category: "runtime",
142
+ proof_handoff_kind: "runtime_anchor",
143
+ default_payment_protocol: defaultPaymentProtocol,
144
+ default_settlement_mode: defaultSettlementMode,
145
+ required_inputs: ["intent_id", "event_type", "event_commitment"],
146
+ optional_inputs: ["payment_protocol", "settlement_mode"]
147
+ },
148
+ {
149
+ class_pack_ref: "transaction.admission.settlement",
150
+ title: "Admission Settlement Transaction",
151
+ description: "Preview admission and submit settlement as one grouped transaction class.",
152
+ workflow_ref: "admission.settlement.flow",
153
+ task_refs: ["admission.preview", "settlement.submit"],
154
+ category: "admission",
155
+ proof_handoff_kind: "admission_settlement",
156
+ default_payment_protocol: defaultPaymentProtocol,
157
+ default_settlement_mode: defaultSettlementMode,
158
+ required_inputs: ["source_zone_id", "target_zone_id", "intent_id"],
159
+ optional_inputs: ["interaction_class", "payment_protocol", "settlement_mode"]
160
+ },
161
+ {
162
+ class_pack_ref: "transaction.registry.anchor",
163
+ title: "Registry Anchor Transaction",
164
+ description: "Register a record and anchor its commitment as one grouped transaction class.",
165
+ workflow_ref: "registry.anchor.flow",
166
+ task_refs: ["registry.register", "anchoring.submit"],
167
+ category: "registry",
168
+ proof_handoff_kind: "registry_anchor",
169
+ default_payment_protocol: defaultPaymentProtocol,
170
+ default_settlement_mode: defaultSettlementMode,
171
+ required_inputs: ["subject_id", "record_type", "commitment_hash"],
172
+ optional_inputs: ["payment_protocol", "settlement_mode"]
173
+ },
174
+ {
175
+ class_pack_ref: "transaction.job.commitment",
176
+ title: "Job Commitment Transaction",
177
+ description: "Quote, reserve, and commit a job as one grouped transaction class.",
178
+ workflow_ref: "job.commitment.flow",
179
+ task_refs: ["jobs.quote", "jobs.reserve", "jobs.commit"],
180
+ category: "jobs",
181
+ proof_handoff_kind: "job_commitment",
182
+ default_payment_protocol: defaultPaymentProtocol,
183
+ default_settlement_mode: defaultSettlementMode,
184
+ required_inputs: ["job_type", "job_id"],
185
+ optional_inputs: ["payment_protocol", "settlement_mode"]
186
+ }
187
+ ];
188
+ }
189
+
113
190
  function buildDefaultTransactionCenter() {
114
191
  const settlementProfiles = Array.isArray(catalog.settlement_profiles) ? catalog.settlement_profiles : [];
115
192
  const defaultSettlementProfile = settlementProfiles[0] || null;
@@ -312,6 +389,42 @@ function getDefaultTransactionGuidedLoop(ref) {
312
389
  return buildDefaultTransactionGuidedLoops().find((entry) => entry && entry.loop_ref === normalized) || null;
313
390
  }
314
391
 
392
+ function buildTransactionClassPackCatalog() {
393
+ const center = buildDefaultTransactionCenter();
394
+ const packs = buildTransactionClassPacks();
395
+ return {
396
+ ok: true,
397
+ brand: center.brand,
398
+ product: "transaction class packs",
399
+ default_payment_protocol: center.default_payment && center.default_payment.protocol ? center.default_payment.protocol : null,
400
+ default_settlement_mode: center.default_settlement && center.default_settlement.settlement_mode ? center.default_settlement.settlement_mode : null,
401
+ class_pack_count: packs.length,
402
+ class_packs: packs
403
+ };
404
+ }
405
+
406
+ function summarizeTransactionClassPacks() {
407
+ const catalogResponse = buildTransactionClassPackCatalog();
408
+ const packs = Array.isArray(catalogResponse.class_packs) ? catalogResponse.class_packs : [];
409
+ return {
410
+ ok: true,
411
+ brand: catalogResponse.brand,
412
+ product: catalogResponse.product,
413
+ default_payment_protocol: catalogResponse.default_payment_protocol,
414
+ default_settlement_mode: catalogResponse.default_settlement_mode,
415
+ class_pack_count: packs.length,
416
+ class_pack_refs: packs.map((entry) => entry && entry.class_pack_ref).filter(Boolean),
417
+ categories: Array.from(new Set(packs.map((entry) => entry && entry.category).filter(Boolean))),
418
+ class_packs: packs
419
+ };
420
+ }
421
+
422
+ function getTransactionClassPack(ref) {
423
+ const normalized = String(ref || "").trim();
424
+ if (!normalized) return null;
425
+ return buildTransactionClassPacks().find((entry) => entry && entry.class_pack_ref === normalized) || null;
426
+ }
427
+
315
428
  function buildCatalogResponse() {
316
429
  return {
317
430
  ok: true,
@@ -447,9 +560,11 @@ module.exports = {
447
560
  buildDefaultTransactionCenter,
448
561
  buildDefaultTransactionGuidedLoopCatalog,
449
562
  buildDefaultTransactionTaskPackCatalog,
563
+ buildTransactionClassPackCatalog,
450
564
  getCatalog,
451
565
  getDefaultTransactionGuidedLoop,
452
566
  getDefaultTransactionTaskPack,
567
+ getTransactionClassPack,
453
568
  getTaskDetail,
454
569
  getWorkflowDetail,
455
570
  getWorkflowList,
@@ -457,5 +572,6 @@ module.exports = {
457
572
  summarizeDefaultTransactionCenter,
458
573
  summarizeDefaultTransactionEconomics,
459
574
  summarizeDefaultTransactionGuidedLoops,
460
- summarizeDefaultTransactionTaskPacks
575
+ summarizeDefaultTransactionTaskPacks,
576
+ summarizeTransactionClassPacks
461
577
  };
@@ -1070,6 +1070,25 @@ function summarizeDefaultGuidedLoopBundlePayload(payload) {
1070
1070
  };
1071
1071
  }
1072
1072
 
1073
+ function summarizeProofHandoffPayload(payload) {
1074
+ const item = payload && typeof payload === "object" ? payload : {};
1075
+ const bundle = item.handoff_bundle && typeof item.handoff_bundle === "object" ? item.handoff_bundle : {};
1076
+ return {
1077
+ ok: item.ok === true,
1078
+ source_ref: item.source_ref || null,
1079
+ transaction_id: item.transaction_id || null,
1080
+ receipt_id: item.receipt_id || null,
1081
+ proof_ref: item.proof_ref || null,
1082
+ settlement_mode: item.settlement_mode || null,
1083
+ payment_protocol: item.payment_protocol || null,
1084
+ proof_ready: item.proof_ready === true,
1085
+ recommended_proof_loop: item.recommended_proof_loop || null,
1086
+ delivery_count: Number(bundle.delivery_count || 0),
1087
+ payment_ledger_count: Number(bundle.payment_ledger_count || 0),
1088
+ task_refs: Array.isArray(bundle.task_refs) ? bundle.task_refs : []
1089
+ };
1090
+ }
1091
+
1073
1092
  function buildCatalogSummarySource(client) {
1074
1093
  const baseCatalog = client && client.catalogCache && typeof client.catalogCache === "object"
1075
1094
  ? client.catalogCache
@@ -2609,6 +2628,30 @@ class CommerceClient {
2609
2628
  return result && result.data && result.data.loop ? result.data.loop : null;
2610
2629
  }
2611
2630
 
2631
+ async getTransactionClassPacks(forceRefresh) {
2632
+ if (!forceRefresh && this.catalogSummaryCache && this.catalogSummaryCache.transactionClassPacks) {
2633
+ return this.catalogSummaryCache.transactionClassPacks;
2634
+ }
2635
+ const result = await this.getJson("/v1/transaction-center/transaction-class-packs");
2636
+ if (!forceRefresh) {
2637
+ this.catalogSummaryCache = this.catalogSummaryCache || {};
2638
+ this.catalogSummaryCache.transactionClassPacks = result.data;
2639
+ }
2640
+ return result.data;
2641
+ }
2642
+
2643
+ async getTransactionClassPacksSummary(forceRefresh) {
2644
+ const result = await this.getJson("/v1/transaction-center/transaction-class-packs/summary");
2645
+ return result && result.data ? result.data : { ok: true, class_pack_count: 0, class_pack_refs: [], class_packs: [] };
2646
+ }
2647
+
2648
+ async getTransactionClassPack(classPackRef, forceRefresh) {
2649
+ const normalized = String(classPackRef || "").trim();
2650
+ if (!normalized) return null;
2651
+ const result = await this.getJson(`/v1/transaction-center/transaction-class-pack?ref=${encodeURIComponent(normalized)}`);
2652
+ return result && result.data && result.data.class_pack ? result.data.class_pack : null;
2653
+ }
2654
+
2612
2655
  async listSettlementPayees(forceRefresh) {
2613
2656
  const summary = await this.getSettlementPayeeSummaries(forceRefresh);
2614
2657
  return extractSummaryValues(summary, "settlement_payees", "payee_agent_id");
@@ -3834,6 +3877,35 @@ class CommerceClient {
3834
3877
  return this.summarizeDefaultGuidedLoopBundle(result);
3835
3878
  }
3836
3879
 
3880
+ async runTransactionClassPack(classPackRef, body, options) {
3881
+ const opts = options || {};
3882
+ return this.runNamedTaskRoute("/v1/transaction-center/transaction-class-packs/run", {
3883
+ command: opts.command || String(classPackRef || "").trim() || "transaction.class.pack.run",
3884
+ class_pack_ref: String(classPackRef || "").trim(),
3885
+ body: body || {},
3886
+ callback_url: opts.callbackUrl || null,
3887
+ settlement_mode: opts.settlementMode || null,
3888
+ payment_protocol: opts.paymentProtocol || null,
3889
+ protocol: opts.protocol || null,
3890
+ integration_id: opts.integrationId || null,
3891
+ integration_ids: Array.isArray(opts.integrationIds) ? opts.integrationIds : [],
3892
+ integration_context: opts.integrationContext || null
3893
+ });
3894
+ }
3895
+
3896
+ async runTransactionClassPackSummary(classPackRef, body, options) {
3897
+ const result = await this.runTransactionClassPack(classPackRef, body, options);
3898
+ return {
3899
+ ok: result && result.ok === true,
3900
+ class_pack_ref: result && result.class_pack ? result.class_pack.class_pack_ref || null : null,
3901
+ workflow_ref: result && result.class_pack ? result.class_pack.workflow_ref || null : null,
3902
+ result_set_summary: result && result.result_set_summary ? result.result_set_summary : null,
3903
+ linked_record_summary: result && result.linked_record_summary ? result.linked_record_summary : null,
3904
+ activity_summary: result && result.activity_summary ? result.activity_summary : null,
3905
+ proof_handoff_summary: this.summarizeProofHandoff(result && result.proof_handoff_summary ? result.proof_handoff_summary : null)
3906
+ };
3907
+ }
3908
+
3837
3909
  async runNamedTaskRoute(path, payload) {
3838
3910
  if (!this.apiKey || !this.walletId || !this.walletSecret) {
3839
3911
  throw new Error("named task routes require apiKey, walletId, and walletSecret");
@@ -5329,6 +5401,10 @@ class CommerceClient {
5329
5401
  return summarizeDefaultGuidedLoopBundlePayload(payload);
5330
5402
  }
5331
5403
 
5404
+ summarizeProofHandoff(payload) {
5405
+ return summarizeProofHandoffPayload(payload);
5406
+ }
5407
+
5332
5408
  summarizeTask(task) {
5333
5409
  return summarizeCatalogTask(task);
5334
5410
  }
@@ -6084,6 +6160,7 @@ module.exports = {
6084
6160
  summarizeDefaultTransactionEconomicsPayload,
6085
6161
  summarizeDefaultTaskPackCatalogPayload,
6086
6162
  summarizeDefaultGuidedLoopBundlePayload,
6163
+ summarizeProofHandoffPayload,
6087
6164
  summarizeActivitySnapshotPayload,
6088
6165
  summarizeOpenIssuesPayload,
6089
6166
  summarizeExecutionExceptionsPayload,
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "xytara",
3
- "version": "1.6.0",
3
+ "version": "1.7.0",
4
4
  "description": "Machine commerce SDK for discovery, quoting, execution, lifecycle inspection, and adapters.",
5
5
  "main": "index.js",
6
6
  "type": "commonjs",
package/server.js CHANGED
@@ -8,9 +8,11 @@ const {
8
8
  buildDefaultTransactionEconomics,
9
9
  buildDefaultTransactionGuidedLoopCatalog,
10
10
  buildDefaultTransactionTaskPackCatalog,
11
+ buildTransactionClassPackCatalog,
11
12
  getCatalog,
12
13
  getDefaultTransactionGuidedLoop,
13
14
  getDefaultTransactionTaskPack,
15
+ getTransactionClassPack,
14
16
  getTaskDetail,
15
17
  getWorkflowDetail,
16
18
  getWorkflowList,
@@ -18,7 +20,8 @@ const {
18
20
  summarizeDefaultTransactionCenter,
19
21
  summarizeDefaultTransactionEconomics,
20
22
  summarizeDefaultTransactionGuidedLoops,
21
- summarizeDefaultTransactionTaskPacks
23
+ summarizeDefaultTransactionTaskPacks,
24
+ summarizeTransactionClassPacks
22
25
  } = require("./lib/catalog_contract");
23
26
  const {
24
27
  createCommandResult,
@@ -364,6 +367,145 @@ function buildDefaultTransactionTaskPackInvokePayload(body) {
364
367
  return null;
365
368
  }
366
369
 
370
+ function buildTransactionClassPackRunPayload(body) {
371
+ const requestBody = body && typeof body === "object" && !Array.isArray(body) ? body : {};
372
+ const packBody = requestBody.body && typeof requestBody.body === "object" && !Array.isArray(requestBody.body)
373
+ ? requestBody.body
374
+ : requestBody;
375
+ const classPackRef = String(requestBody.class_pack_ref || "").trim();
376
+ const integrationIds = Array.isArray(requestBody.integration_ids) && requestBody.integration_ids.length > 0
377
+ ? requestBody.integration_ids
378
+ : ["builtin.payment.x402", "builtin.settlement.chain"];
379
+
380
+ if (classPackRef === "transaction.trust.receipt") {
381
+ return buildNamedTaskSetPayload([
382
+ {
383
+ task_id: "task_1",
384
+ task_ref: "trust.verify",
385
+ body: { subject_id: packBody.subject_id }
386
+ },
387
+ {
388
+ task_id: "task_2",
389
+ task_ref: "receipt.validate",
390
+ body: { receipt_id: packBody.receipt_id }
391
+ }
392
+ ], {
393
+ ...requestBody,
394
+ ...packBody,
395
+ payment_protocol: requestBody.payment_protocol || "x402",
396
+ integration_ids: integrationIds,
397
+ settlement_mode: requestBody.settlement_mode || "evm_payment"
398
+ }, requestBody.command || classPackRef);
399
+ }
400
+
401
+ if (classPackRef === "transaction.runtime.consequence") {
402
+ return buildNamedTaskSetPayload([
403
+ {
404
+ task_id: "task_1",
405
+ task_ref: "runtime.emit",
406
+ body: {
407
+ intent_id: packBody.intent_id,
408
+ event_type: packBody.event_type
409
+ }
410
+ },
411
+ {
412
+ task_id: "task_2",
413
+ task_ref: "runtime.anchor",
414
+ body: {
415
+ event_commitment: packBody.event_commitment
416
+ }
417
+ }
418
+ ], {
419
+ ...requestBody,
420
+ ...packBody,
421
+ payment_protocol: requestBody.payment_protocol || "x402",
422
+ integration_ids: integrationIds,
423
+ settlement_mode: requestBody.settlement_mode || "evm_payment"
424
+ }, requestBody.command || classPackRef);
425
+ }
426
+
427
+ if (classPackRef === "transaction.admission.settlement") {
428
+ return buildNamedTaskSetPayload([
429
+ {
430
+ task_id: "task_1",
431
+ task_ref: "admission.preview",
432
+ body: {
433
+ source_zone_id: packBody.source_zone_id,
434
+ target_zone_id: packBody.target_zone_id,
435
+ interaction_class: packBody.interaction_class
436
+ }
437
+ },
438
+ {
439
+ task_id: "task_2",
440
+ task_ref: "settlement.submit",
441
+ body: {
442
+ intent_id: packBody.intent_id
443
+ }
444
+ }
445
+ ], {
446
+ ...requestBody,
447
+ ...packBody,
448
+ payment_protocol: requestBody.payment_protocol || "x402",
449
+ integration_ids: integrationIds,
450
+ settlement_mode: requestBody.settlement_mode || "evm_payment"
451
+ }, requestBody.command || classPackRef);
452
+ }
453
+
454
+ if (classPackRef === "transaction.registry.anchor") {
455
+ return buildNamedTaskSetPayload([
456
+ {
457
+ task_id: "task_1",
458
+ task_ref: "registry.register",
459
+ body: {
460
+ subject_id: packBody.subject_id,
461
+ record_type: packBody.record_type
462
+ }
463
+ },
464
+ {
465
+ task_id: "task_2",
466
+ task_ref: "anchoring.submit",
467
+ body: {
468
+ commitment_hash: packBody.commitment_hash
469
+ }
470
+ }
471
+ ], {
472
+ ...requestBody,
473
+ ...packBody,
474
+ payment_protocol: requestBody.payment_protocol || "x402",
475
+ integration_ids: integrationIds,
476
+ settlement_mode: requestBody.settlement_mode || "evm_payment"
477
+ }, requestBody.command || classPackRef);
478
+ }
479
+
480
+ if (classPackRef === "transaction.job.commitment") {
481
+ return buildNamedTaskSetPayload([
482
+ {
483
+ task_id: "task_1",
484
+ task_ref: "jobs.quote",
485
+ body: { job_type: packBody.job_type }
486
+ },
487
+ {
488
+ task_id: "task_2",
489
+ task_ref: "jobs.reserve",
490
+ body: { job_id: packBody.job_id }
491
+ },
492
+ {
493
+ task_id: "task_3",
494
+ task_ref: "jobs.commit",
495
+ body: { job_id: packBody.job_id }
496
+ }
497
+ ], {
498
+ ...requestBody,
499
+ ...packBody,
500
+ payment_protocol: requestBody.payment_protocol || "x402",
501
+ integration_ids: integrationIds,
502
+ settlement_mode: requestBody.settlement_mode || "evm_payment"
503
+ }, requestBody.command || classPackRef);
504
+ }
505
+
506
+ return null;
507
+ }
508
+
367
509
  function listTransactionRecords(filters) {
368
510
  const transactions = Array.from(state.transactions.values()).map((item) => item.transaction);
369
511
  return listRecords(new Map(transactions.map((item) => [item.transaction_id, item])), filters);
@@ -481,6 +623,35 @@ function buildGuidedLoopBundle(loopRef, result) {
481
623
  };
482
624
  }
483
625
 
626
+ function buildProofHandoffSummary(result, sourceRef) {
627
+ const resultSet = buildResultSetFromCommandResult(result);
628
+ const linked = buildLinkedRecordSetFromCommandResult(result);
629
+ const receipt = resultSet.receipt || {};
630
+ const transaction = resultSet.transaction || {};
631
+ return {
632
+ ok: true,
633
+ source_ref: sourceRef || null,
634
+ transaction_id: transaction.transaction_id || null,
635
+ receipt_id: receipt.receipt_id || null,
636
+ proof_ref: receipt.proof_ref || null,
637
+ settlement_mode: transaction.settlement && transaction.settlement.mode ? transaction.settlement.mode : null,
638
+ payment_protocol: transaction.payment && transaction.payment.protocol ? transaction.payment.protocol : null,
639
+ proof_ready: Boolean(receipt.receipt_id && receipt.proof_ref),
640
+ recommended_proof_loop: "default.proof.bundle.loop",
641
+ recommended_xoonya_surface: "/v1/proof-center/default-loops/run",
642
+ handoff_bundle: {
643
+ transaction_id: transaction.transaction_id || null,
644
+ receipt_id: receipt.receipt_id || null,
645
+ proof_ref: receipt.proof_ref || null,
646
+ task_refs: transaction.execution && transaction.execution.results_by_task_id
647
+ ? Object.values(transaction.execution.results_by_task_id).map((entry) => entry && entry.task_ref).filter(Boolean)
648
+ : [],
649
+ delivery_count: Array.isArray(linked.deliveries) ? linked.deliveries.length : 0,
650
+ payment_ledger_count: Array.isArray(linked.payment_ledger) ? linked.payment_ledger.length : 0
651
+ }
652
+ };
653
+ }
654
+
484
655
  function buildOperationsDashboard(filters) {
485
656
  const disputes = listRecords(state.disputes, filters);
486
657
  const refunds = listRecords(state.refunds, filters);
@@ -589,6 +760,26 @@ async function routeRequest(req, res) {
589
760
  return;
590
761
  }
591
762
 
763
+ if (req.method === "GET" && url.pathname === "/v1/transaction-center/transaction-class-packs") {
764
+ sendJson(res, 200, buildTransactionClassPackCatalog());
765
+ return;
766
+ }
767
+
768
+ if (req.method === "GET" && url.pathname === "/v1/transaction-center/transaction-class-packs/summary") {
769
+ sendJson(res, 200, summarizeTransactionClassPacks());
770
+ return;
771
+ }
772
+
773
+ if (req.method === "GET" && url.pathname === "/v1/transaction-center/transaction-class-pack") {
774
+ const pack = getTransactionClassPack(url.searchParams.get("ref"));
775
+ if (!pack) {
776
+ sendJson(res, 404, { ok: false, error: "transaction_class_pack_not_found" });
777
+ return;
778
+ }
779
+ sendJson(res, 200, { ok: true, class_pack: pack });
780
+ return;
781
+ }
782
+
592
783
  if (req.method === "GET" && url.pathname === "/v1/transaction-center/default-loops") {
593
784
  sendJson(res, 200, buildDefaultTransactionGuidedLoopCatalog());
594
785
  return;
@@ -1121,6 +1312,36 @@ async function routeRequest(req, res) {
1121
1312
  return;
1122
1313
  }
1123
1314
 
1315
+ if (req.method === "POST" && url.pathname === "/v1/transaction-center/transaction-class-packs/run") {
1316
+ const body = await readJsonBody(req);
1317
+ const classPackRef = String(body && body.class_pack_ref || "").trim();
1318
+ const pack = getTransactionClassPack(classPackRef);
1319
+ if (!pack) {
1320
+ sendJson(res, 404, { ok: false, error: "transaction_class_pack_not_found" });
1321
+ return;
1322
+ }
1323
+ const payload = buildTransactionClassPackRunPayload(body);
1324
+ if (!payload) {
1325
+ sendJson(res, 404, { ok: false, error: "transaction_class_pack_not_found" });
1326
+ return;
1327
+ }
1328
+ const result = executeCommandRequest(state, payload, req.headers);
1329
+ if (result.status !== 200) {
1330
+ sendJson(res, result.status, result.payload);
1331
+ return;
1332
+ }
1333
+ sendJson(res, 200, {
1334
+ ok: true,
1335
+ class_pack: pack,
1336
+ result: result.payload,
1337
+ result_set_summary: summarizeResultSetPayload(buildResultSetFromCommandResult(result.payload)),
1338
+ linked_record_summary: summarizeLinkedRecordSetPayload(buildLinkedRecordSetFromCommandResult(result.payload)),
1339
+ activity_summary: summarizeActivitySnapshotPayload(buildActivitySnapshotFromCommandResult(result.payload)),
1340
+ proof_handoff_summary: buildProofHandoffSummary(result.payload, classPackRef)
1341
+ });
1342
+ return;
1343
+ }
1344
+
1124
1345
  if (req.method === "POST" && url.pathname === "/x402/mcp/tools/invoke") {
1125
1346
  const body = await readJsonBody(req);
1126
1347
  const payload = buildMcpInvokePayload(body, { paymentProtocol: "x402" });