@lehaotech/walmart-mcp 0.5.4

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (87) hide show
  1. package/.env.example +25 -0
  2. package/CHANGELOG.md +247 -0
  3. package/LICENSE +21 -0
  4. package/README.md +344 -0
  5. package/build/api/advertising/ad-client.d.ts +24 -0
  6. package/build/api/advertising/ad-client.js +174 -0
  7. package/build/api/advertising/advertising-api.d.ts +50 -0
  8. package/build/api/advertising/advertising-api.js +89 -0
  9. package/build/api/client.d.ts +19 -0
  10. package/build/api/client.js +150 -0
  11. package/build/api/feeds/feeds-api.d.ts +15 -0
  12. package/build/api/feeds/feeds-api.js +53 -0
  13. package/build/api/fulfillment/fulfillment-api.d.ts +37 -0
  14. package/build/api/fulfillment/fulfillment-api.js +81 -0
  15. package/build/api/index.d.ts +44 -0
  16. package/build/api/index.js +56 -0
  17. package/build/api/inventory/inventory-api.d.ts +27 -0
  18. package/build/api/inventory/inventory-api.js +49 -0
  19. package/build/api/items/items-api.d.ts +33 -0
  20. package/build/api/items/items-api.js +67 -0
  21. package/build/api/notifications/notifications-api.d.ts +14 -0
  22. package/build/api/notifications/notifications-api.js +33 -0
  23. package/build/api/orders/orders-api.d.ts +32 -0
  24. package/build/api/orders/orders-api.js +47 -0
  25. package/build/api/pricing/pricing-api.d.ts +32 -0
  26. package/build/api/pricing/pricing-api.js +60 -0
  27. package/build/api/reports/reports-api.d.ts +37 -0
  28. package/build/api/reports/reports-api.js +51 -0
  29. package/build/api/returns/returns-api.d.ts +26 -0
  30. package/build/api/returns/returns-api.js +37 -0
  31. package/build/api/settings/settings-api.d.ts +9 -0
  32. package/build/api/settings/settings-api.js +21 -0
  33. package/build/auth/oauth.d.ts +16 -0
  34. package/build/auth/oauth.js +125 -0
  35. package/build/config/environment.d.ts +22 -0
  36. package/build/config/environment.js +50 -0
  37. package/build/index.d.ts +2 -0
  38. package/build/index.js +180 -0
  39. package/build/scripts/client-configs.d.ts +36 -0
  40. package/build/scripts/client-configs.js +132 -0
  41. package/build/scripts/diagnose.d.ts +15 -0
  42. package/build/scripts/diagnose.js +320 -0
  43. package/build/scripts/setup.d.ts +17 -0
  44. package/build/scripts/setup.js +276 -0
  45. package/build/tools/definitions/advertising.d.ts +664 -0
  46. package/build/tools/definitions/advertising.js +315 -0
  47. package/build/tools/definitions/discovery.d.ts +24 -0
  48. package/build/tools/definitions/discovery.js +65 -0
  49. package/build/tools/definitions/feeds.d.ts +46 -0
  50. package/build/tools/definitions/feeds.js +42 -0
  51. package/build/tools/definitions/fulfillment.d.ts +1127 -0
  52. package/build/tools/definitions/fulfillment.js +272 -0
  53. package/build/tools/definitions/inventory.d.ts +392 -0
  54. package/build/tools/definitions/inventory.js +182 -0
  55. package/build/tools/definitions/items.d.ts +447 -0
  56. package/build/tools/definitions/items.js +223 -0
  57. package/build/tools/definitions/notifications.d.ts +84 -0
  58. package/build/tools/definitions/notifications.js +73 -0
  59. package/build/tools/definitions/orders.d.ts +2659 -0
  60. package/build/tools/definitions/orders.js +298 -0
  61. package/build/tools/definitions/pricing.d.ts +724 -0
  62. package/build/tools/definitions/pricing.js +254 -0
  63. package/build/tools/definitions/reports.d.ts +223 -0
  64. package/build/tools/definitions/reports.js +144 -0
  65. package/build/tools/definitions/returns.d.ts +441 -0
  66. package/build/tools/definitions/returns.js +126 -0
  67. package/build/tools/definitions/settings.d.ts +100 -0
  68. package/build/tools/definitions/settings.js +52 -0
  69. package/build/tools/definitions/shared-schemas.d.ts +40 -0
  70. package/build/tools/definitions/shared-schemas.js +47 -0
  71. package/build/tools/definitions/token-management.d.ts +16 -0
  72. package/build/tools/definitions/token-management.js +41 -0
  73. package/build/tools/index.d.ts +6924 -0
  74. package/build/tools/index.js +379 -0
  75. package/build/utils/api-error.d.ts +41 -0
  76. package/build/utils/api-error.js +97 -0
  77. package/build/utils/endpoint-catalog.d.ts +22 -0
  78. package/build/utils/endpoint-catalog.js +89 -0
  79. package/build/utils/env-file.d.ts +12 -0
  80. package/build/utils/env-file.js +27 -0
  81. package/build/utils/known-issues.d.ts +29 -0
  82. package/build/utils/known-issues.js +122 -0
  83. package/build/utils/logger.d.ts +15 -0
  84. package/build/utils/logger.js +56 -0
  85. package/build/utils/rate-limiter.d.ts +51 -0
  86. package/build/utils/rate-limiter.js +109 -0
  87. package/package.json +1 -0
@@ -0,0 +1,379 @@
1
+ import { upsertEnvVars } from '../utils/env-file.js';
2
+ import { tokenManagementTools } from './definitions/token-management.js';
3
+ import { itemTools } from './definitions/items.js';
4
+ import { inventoryTools } from './definitions/inventory.js';
5
+ import { orderTools } from './definitions/orders.js';
6
+ import { pricingTools } from './definitions/pricing.js';
7
+ import { feedTools } from './definitions/feeds.js';
8
+ import { fulfillmentTools } from './definitions/fulfillment.js';
9
+ import { returnTools } from './definitions/returns.js';
10
+ import { reportTools } from './definitions/reports.js';
11
+ import { notificationTools } from './definitions/notifications.js';
12
+ import { advertisingTools } from './definitions/advertising.js';
13
+ import { settingsTools } from './definitions/settings.js';
14
+ import { discoveryTools } from './definitions/discovery.js';
15
+ import { searchEndpoints } from '../utils/endpoint-catalog.js';
16
+ export function getToolDefinitions() {
17
+ return [
18
+ ...tokenManagementTools,
19
+ ...itemTools,
20
+ ...inventoryTools,
21
+ ...orderTools,
22
+ ...pricingTools,
23
+ ...feedTools,
24
+ ...fulfillmentTools,
25
+ ...returnTools,
26
+ ...reportTools,
27
+ ...notificationTools,
28
+ ...advertisingTools,
29
+ ...settingsTools,
30
+ ...discoveryTools,
31
+ ];
32
+ }
33
+ export async function executeTool(api, toolName, args) {
34
+ switch (toolName) {
35
+ // ===== Token Management =====
36
+ case 'walmart_get_token':
37
+ await api.auth.refreshToken();
38
+ return api.auth.getTokenInfo();
39
+ case 'walmart_get_token_status':
40
+ return await api.auth.getTokenDetail();
41
+ case 'walmart_get_token_info':
42
+ return api.auth.getTokenInfo();
43
+ case 'walmart_set_credentials': {
44
+ upsertEnvVars({
45
+ WALMART_CLIENT_ID: args.clientId,
46
+ WALMART_CLIENT_SECRET: args.clientSecret,
47
+ });
48
+ return { success: true, message: 'Credentials saved to .env. Restart the server to apply.' };
49
+ }
50
+ case 'walmart_display_credentials':
51
+ return {
52
+ clientId: process.env.WALMART_CLIENT_ID || '(not set)',
53
+ clientSecret: process.env.WALMART_CLIENT_SECRET
54
+ ? `${process.env.WALMART_CLIENT_SECRET.substring(0, 8)}...${process.env.WALMART_CLIENT_SECRET.slice(-4)}`
55
+ : '(not set)',
56
+ environment: process.env.WALMART_ENVIRONMENT || 'sandbox',
57
+ market: process.env.WALMART_MARKET || 'us',
58
+ svcName: process.env.WALMART_SVC_NAME || 'Walmart Marketplace',
59
+ };
60
+ case 'walmart_setup_guide': {
61
+ const hasMarketplaceCreds = !!(process.env.WALMART_CLIENT_ID && process.env.WALMART_CLIENT_SECRET);
62
+ const hasAdCreds = !!(process.env.WALMART_AD_CONSUMER_ID && process.env.WALMART_AD_PRIVATE_KEY);
63
+ const environment = process.env.WALMART_ENVIRONMENT || 'sandbox';
64
+ return {
65
+ status: hasMarketplaceCreds ? 'ready' : 'credentials_required',
66
+ configured: {
67
+ marketplaceCredentials: hasMarketplaceCreds,
68
+ advertisingCredentials: hasAdCreds,
69
+ environment,
70
+ market: process.env.WALMART_MARKET || 'us',
71
+ },
72
+ steps: [
73
+ '1. Get API credentials: sign in at https://developer.walmart.com/, create an app under Marketplace, and copy the Client ID and Client Secret.',
74
+ '2. Provide credentials one of two ways: (a) set WALMART_CLIENT_ID and WALMART_CLIENT_SECRET in your MCP server "env" (or a .env file in the project root) and restart, or (b) call the walmart_set_credentials tool now with your Client ID and Secret.',
75
+ '3. Choose the environment: set WALMART_ENVIRONMENT to "sandbox" (default, for testing) or "production" (for live selling).',
76
+ '4. Verify: call walmart_get_token to confirm authentication works, then walmart_display_credentials to review the active configuration.',
77
+ '5. (Optional) For Walmart Connect advertising tools, also set WALMART_AD_CONSUMER_ID and WALMART_AD_PRIVATE_KEY (apply at https://www.walmartconnect.com/).',
78
+ ],
79
+ nextAction: hasMarketplaceCreds
80
+ ? 'Credentials are set. Call walmart_get_token to verify, then use any tool.'
81
+ : 'No marketplace credentials yet. Call walmart_set_credentials, or set the env vars and restart.',
82
+ docs: 'https://developer.walmart.com/',
83
+ };
84
+ }
85
+ case 'walmart_get_rate_budget': {
86
+ const status = api.getRateLimiterStatus();
87
+ return {
88
+ ...status,
89
+ notes: [
90
+ 'localRemaining = requests this MCP can issue right now under the sliding-window limiter.',
91
+ 'serverTokensRemaining = most recent x-current-token-count from Walmart (null if no API call has been made yet).',
92
+ 'serverReplenishTime = most recent x-next-replenish-time (ISO 8601) — when Walmart will top your bucket back up.',
93
+ 'Walmart Marketplace does not have an OAuth user-token flow; rate limits depend on your seller-account tier.',
94
+ ],
95
+ };
96
+ }
97
+ // ===== Items =====
98
+ case 'walmart_get_all_items':
99
+ return await api.items.getAllItems(args);
100
+ case 'walmart_get_item':
101
+ return await api.items.getItem(args.sku);
102
+ case 'walmart_retire_item':
103
+ return await api.items.retireItem(args.sku);
104
+ case 'walmart_bulk_retire_items':
105
+ return await api.items.bulkRetireItems(args.skus);
106
+ case 'walmart_get_item_count':
107
+ return await api.items.getItemCount(args);
108
+ case 'walmart_get_taxonomy':
109
+ return await api.items.getTaxonomy();
110
+ case 'walmart_get_item_spec':
111
+ return await api.items.getItemSpec(args);
112
+ case 'walmart_submit_item_feed':
113
+ return await api.items.submitItemFeed(args.feedData);
114
+ case 'walmart_submit_item_update_feed':
115
+ return await api.items.submitItemUpdateFeed(args.feedData);
116
+ case 'walmart_submit_wfs_item_feed':
117
+ return await api.items.submitWfsItemFeed(args.feedData);
118
+ case 'walmart_convert_to_wfs':
119
+ return await api.items.convertToWfs(args.feedData);
120
+ case 'walmart_get_hazmat_items':
121
+ return await api.items.getHazmatItems(args.requestData);
122
+ // ===== Inventory =====
123
+ case 'walmart_get_inventory':
124
+ return await api.inventory.getInventory(args.sku);
125
+ case 'walmart_update_inventory':
126
+ return await api.inventory.updateInventory(args);
127
+ case 'walmart_get_inventory_all_nodes':
128
+ return await api.inventory.getInventoryAllNodes(args.sku);
129
+ case 'walmart_update_inventory_multi_node':
130
+ return await api.inventory.updateInventoryMultiNode(args.sku, args.inventoryData);
131
+ case 'walmart_get_all_inventory':
132
+ return await api.inventory.getAllInventory(args);
133
+ case 'walmart_submit_inventory_feed':
134
+ return await api.inventory.submitInventoryFeed(args.feedData);
135
+ case 'walmart_submit_multi_node_inventory_feed':
136
+ return await api.inventory.submitMultiNodeInventoryFeed(args.feedData);
137
+ case 'walmart_get_lag_time':
138
+ return await api.inventory.getLagTime(args.sku);
139
+ case 'walmart_update_lag_time':
140
+ return await api.inventory.updateLagTime(args);
141
+ case 'walmart_submit_lagtime_feed':
142
+ return await api.inventory.submitLagTimeFeed(args.feedData);
143
+ // ===== Orders =====
144
+ case 'walmart_get_all_orders':
145
+ return await api.orders.getAllOrders(args);
146
+ case 'walmart_get_released_orders':
147
+ return await api.orders.getReleasedOrders(args);
148
+ case 'walmart_get_order':
149
+ return await api.orders.getOrder(args.purchaseOrderId);
150
+ case 'walmart_acknowledge_order':
151
+ return await api.orders.acknowledgeOrder(args.purchaseOrderId);
152
+ case 'walmart_ship_order':
153
+ return await api.orders.shipOrder(args.purchaseOrderId, args.shipmentData);
154
+ case 'walmart_cancel_order':
155
+ return await api.orders.cancelOrder(args.purchaseOrderId, args.cancelData);
156
+ case 'walmart_refund_order':
157
+ return await api.orders.refundOrder(args.purchaseOrderId, args.refundData);
158
+ case 'walmart_get_shipping_carriers':
159
+ return await api.orders.getShippingCarriers();
160
+ case 'walmart_create_shipping_label':
161
+ return await api.orders.createShippingLabel(args.labelData);
162
+ case 'walmart_get_shipping_estimate':
163
+ return await api.orders.getShippingEstimate(args.estimateParams);
164
+ // ===== Pricing =====
165
+ case 'walmart_update_price':
166
+ return await api.pricing.updatePrice(args);
167
+ case 'walmart_submit_price_feed':
168
+ return await api.pricing.submitPriceFeed(args.feedData);
169
+ case 'walmart_submit_mp_price_feed':
170
+ return await api.pricing.submitMpPriceFeed(args.feedData);
171
+ case 'walmart_submit_promo_price_feed':
172
+ return await api.pricing.submitPromoPriceFeed(args.feedData);
173
+ case 'walmart_get_repricer_strategies':
174
+ return await api.pricing.getRepricerStrategies();
175
+ case 'walmart_create_repricer_strategy':
176
+ return await api.pricing.createRepricerStrategy(args.strategyData);
177
+ case 'walmart_update_repricer_strategy':
178
+ return await api.pricing.updateRepricerStrategy(args.strategyData);
179
+ case 'walmart_delete_repricer_strategy':
180
+ return await api.pricing.deleteRepricerStrategy(args.strategyId);
181
+ case 'walmart_assign_items_to_strategy':
182
+ return await api.pricing.assignItemsToStrategy(args);
183
+ case 'walmart_unassign_items_from_strategy':
184
+ return await api.pricing.unassignItemsFromStrategy(args);
185
+ // ===== Feeds =====
186
+ case 'walmart_get_all_feed_statuses':
187
+ return await api.feeds.getAllFeedStatuses(args);
188
+ case 'walmart_get_feed_status':
189
+ return await api.feeds.getFeedStatus(args.feedId);
190
+ case 'walmart_get_feed_item_status':
191
+ return await api.feeds.getFeedItemStatus(args.feedId);
192
+ case 'walmart_submit_generic_feed':
193
+ return await api.feeds.submitFeed(args.feedType, args.feedData);
194
+ case 'walmart_poll_feed_until_complete': {
195
+ const maxWaitMs = args.maxWaitSeconds
196
+ ? args.maxWaitSeconds * 1000
197
+ : undefined;
198
+ return await api.feeds.pollFeedUntilComplete(args.feedId, maxWaitMs);
199
+ }
200
+ // ===== WFS Fulfillment =====
201
+ case 'walmart_create_inbound_order':
202
+ return await api.fulfillment.createInboundOrder(args.orderData);
203
+ case 'walmart_get_inbound_shipments':
204
+ return await api.fulfillment.getInboundShipments(args);
205
+ case 'walmart_get_inbound_errors':
206
+ return await api.fulfillment.getInboundErrors(args);
207
+ case 'walmart_get_shipment_items':
208
+ return await api.fulfillment.getShipmentItems(args);
209
+ case 'walmart_get_shipment_quantities':
210
+ return await api.fulfillment.getShipmentQuantities(args);
211
+ case 'walmart_get_shipment_label':
212
+ return await api.fulfillment.getShipmentLabel(args.shipmentId);
213
+ case 'walmart_update_shipment_tracking':
214
+ return await api.fulfillment.updateShipmentTracking(args.trackingData);
215
+ case 'walmart_cancel_inbound_order':
216
+ return await api.fulfillment.cancelInboundOrder(args.inboundOrderId);
217
+ case 'walmart_get_purchased_label':
218
+ return await api.fulfillment.getShippingLabel(args.purchaseOrderId);
219
+ case 'walmart_get_label_by_tracking':
220
+ return await api.fulfillment.getLabelByTracking(args.carrierId, args.trackingNo);
221
+ case 'walmart_discard_label':
222
+ return await api.fulfillment.discardLabel(args.labelData);
223
+ case 'walmart_get_package_types':
224
+ return await api.fulfillment.getPackageTypes(args.carrierId);
225
+ case 'walmart_create_mcs_order':
226
+ return await api.fulfillment.createMcsOrder(args.orderData);
227
+ case 'walmart_cancel_mcs_order':
228
+ return await api.fulfillment.cancelMcsOrder(args.cancelData);
229
+ case 'walmart_get_mcs_order_status':
230
+ return await api.fulfillment.getMcsOrderStatus(args.orderId);
231
+ case 'walmart_get_carrier_rate_quotes':
232
+ return await api.fulfillment.getCarrierRateQuotes(args.quoteData);
233
+ case 'walmart_book_carrier_shipment':
234
+ return await api.fulfillment.bookCarrierShipment(args.bookingData);
235
+ case 'walmart_get_carrier_label':
236
+ return await api.fulfillment.getCarrierLabel(args.shipmentId);
237
+ case 'walmart_schedule_carrier_pickup':
238
+ return await api.fulfillment.scheduleCarrierPickup(args.pickupData);
239
+ // ===== Returns & Refunds =====
240
+ case 'walmart_get_all_returns':
241
+ return await api.returns.getAllReturns(args);
242
+ case 'walmart_get_return':
243
+ return await api.returns.getReturn(args.returnOrderId);
244
+ case 'walmart_approve_return':
245
+ return await api.returns.approveReturn(args.approvalData);
246
+ case 'walmart_reject_return':
247
+ return await api.returns.rejectReturn(args.rejectionData);
248
+ case 'walmart_issue_return_refund':
249
+ return await api.returns.issueReturnRefund(args.returnOrderId, args.itemId, args.refundData);
250
+ case 'walmart_generate_return_label':
251
+ return await api.returns.generateReturnLabel(args.returnOrderId, args.itemId, args.labelData);
252
+ case 'walmart_get_wfs_returns':
253
+ return await api.returns.getWfsReturns(args);
254
+ case 'walmart_get_return_count':
255
+ return await api.returns.getReturnCount(args);
256
+ // ===== Reports & Analytics =====
257
+ case 'walmart_create_report':
258
+ return await api.reports.createReport(args.reportData);
259
+ case 'walmart_get_report_requests':
260
+ return await api.reports.getReportRequests(args);
261
+ case 'walmart_get_report_status':
262
+ return await api.reports.getReportStatus(args.requestId);
263
+ case 'walmart_download_report':
264
+ return await api.reports.downloadReport(args);
265
+ case 'walmart_create_report_schedule':
266
+ return await api.reports.createReportSchedule(args.scheduleData);
267
+ case 'walmart_get_report_schedules':
268
+ return await api.reports.getReportSchedules(args);
269
+ case 'walmart_update_report_schedule':
270
+ return await api.reports.updateReportSchedule(args.scheduleId, args.scheduleData);
271
+ case 'walmart_delete_report_schedule':
272
+ return await api.reports.deleteReportSchedule(args.scheduleId);
273
+ case 'walmart_get_unpublished_items':
274
+ return await api.reports.getUnpublishedItems(args);
275
+ case 'walmart_get_listing_quality':
276
+ return await api.reports.getListingQuality(args);
277
+ case 'walmart_get_quality_categories':
278
+ return await api.reports.getQualityCategories(args);
279
+ case 'walmart_get_item_quality_details':
280
+ return await api.reports.getItemQualityDetails(args);
281
+ // ===== Notifications =====
282
+ case 'walmart_create_subscription':
283
+ return await api.notifications.createSubscription(args.subscriptionData);
284
+ case 'walmart_get_subscriptions':
285
+ return await api.notifications.getSubscriptions(args);
286
+ case 'walmart_get_subscription':
287
+ return await api.notifications.getSubscription(args.subscriptionId);
288
+ case 'walmart_update_subscription':
289
+ return await api.notifications.updateSubscription(args.subscriptionId, args.subscriptionData);
290
+ case 'walmart_delete_subscription':
291
+ return await api.notifications.deleteSubscription(args.subscriptionId);
292
+ case 'walmart_test_subscription':
293
+ return await api.notifications.testSubscription(args.subscriptionId);
294
+ // ===== Advertising (Walmart Connect) =====
295
+ case 'walmart_ad_get_campaigns':
296
+ return await api.advertising.getCampaigns(args);
297
+ case 'walmart_ad_create_campaign':
298
+ return await api.advertising.createCampaign(args.campaignData);
299
+ case 'walmart_ad_update_campaign':
300
+ return await api.advertising.updateCampaign(args.campaignData);
301
+ case 'walmart_ad_delete_campaign':
302
+ return await api.advertising.deleteCampaign(args.deleteData);
303
+ case 'walmart_ad_get_ad_groups':
304
+ return await api.advertising.getAdGroups(args);
305
+ case 'walmart_ad_create_ad_groups':
306
+ return await api.advertising.createAdGroups(args.adGroupData);
307
+ case 'walmart_ad_update_ad_groups':
308
+ return await api.advertising.updateAdGroups(args.adGroupData);
309
+ case 'walmart_ad_get_ad_items':
310
+ return await api.advertising.getAdItems(args);
311
+ case 'walmart_ad_add_ad_items':
312
+ return await api.advertising.addAdItems(args.itemData);
313
+ case 'walmart_ad_update_ad_items':
314
+ return await api.advertising.updateAdItems(args.itemData);
315
+ case 'walmart_ad_get_keywords':
316
+ return await api.advertising.getKeywords(args);
317
+ case 'walmart_ad_add_keywords':
318
+ return await api.advertising.addKeywords(args.keywordData);
319
+ case 'walmart_ad_update_keywords':
320
+ return await api.advertising.updateKeywords(args.keywordData);
321
+ case 'walmart_ad_get_keyword_analytics':
322
+ return await api.advertising.getKeywordAnalytics(args.analyticsData);
323
+ case 'walmart_ad_create_placement_bids':
324
+ return await api.advertising.createPlacementBids(args.bidData);
325
+ case 'walmart_ad_get_placement_bids':
326
+ return await api.advertising.getPlacementBids(args);
327
+ case 'walmart_ad_create_platform_bids':
328
+ return await api.advertising.createPlatformBids(args.bidData);
329
+ case 'walmart_ad_create_report_snapshot':
330
+ return await api.advertising.createReportSnapshot(args.reportData);
331
+ case 'walmart_ad_get_report_snapshots':
332
+ return await api.advertising.getReportSnapshots(args);
333
+ case 'walmart_ad_get_realtime_stats':
334
+ return await api.advertising.getRealtimeStats(args.statsData);
335
+ case 'walmart_ad_get_latest_report_date':
336
+ return await api.advertising.getLatestReportDate();
337
+ case 'walmart_ad_get_item_recommendations':
338
+ return await api.advertising.getItemRecommendations(args.recommendationData);
339
+ case 'walmart_ad_get_keyword_recommendations':
340
+ return await api.advertising.getKeywordRecommendations(args.recommendationData);
341
+ case 'walmart_ad_get_search_trends':
342
+ return await api.advertising.getSearchTrends(args.trendData);
343
+ case 'walmart_ad_get_sba_profile':
344
+ return await api.advertising.getSbaProfile();
345
+ // ===== Settings & Configuration =====
346
+ case 'walmart_get_shipping_settings':
347
+ return await api.settings.getShippingSettings();
348
+ case 'walmart_update_shipping_settings':
349
+ return await api.settings.updateShippingSettings(args.settingsData);
350
+ case 'walmart_get_fulfillment_centers':
351
+ return await api.settings.getFulfillmentCenters();
352
+ case 'walmart_get_partner_info':
353
+ return await api.settings.getPartnerInfo();
354
+ // ===== Discovery / escape hatch =====
355
+ case 'walmart_call_endpoint': {
356
+ const method = args.method.toUpperCase();
357
+ const path = args.path;
358
+ const params = args.params;
359
+ const body = args.body;
360
+ const client = api.getMarketplaceClient();
361
+ switch (method) {
362
+ case 'GET': return await client.get(path, params);
363
+ case 'DELETE': return await client.delete(path, params);
364
+ case 'POST': return await client.post(path, body);
365
+ case 'PUT': return await client.put(path, body);
366
+ case 'PATCH': return await client.post(path, body);
367
+ default:
368
+ throw new Error(`Unsupported HTTP method: ${method}`);
369
+ }
370
+ }
371
+ case 'walmart_search_endpoints': {
372
+ const q = args.query;
373
+ const limit = args.limit ?? 10;
374
+ return { query: q, matches: searchEndpoints(q, limit) };
375
+ }
376
+ default:
377
+ throw new Error(`Unknown tool: ${toolName}`);
378
+ }
379
+ }
@@ -0,0 +1,41 @@
1
+ /**
2
+ * Error raised for a non-2xx Walmart API response.
3
+ *
4
+ * Carries the HTTP status and the raw response body so callers (and the LLM)
5
+ * get the full Walmart error detail instead of a lossy `"HTTP 404: Not Found"`
6
+ * string. Additional context fields (endpoint / tool / hint) are populated by
7
+ * the request interceptor and the tool dispatcher so the LLM sees:
8
+ * - which Walmart endpoint failed
9
+ * - which MCP tool triggered it
10
+ * - a workaround hint for known-broken Walmart endpoints (Known Issues table)
11
+ */
12
+ export declare class WalmartApiError extends Error {
13
+ readonly status: number;
14
+ readonly details?: unknown | undefined;
15
+ /** Method + path of the Walmart call, e.g. "GET /v3/returns/count". */
16
+ readonly endpoint?: string | undefined;
17
+ /** MCP tool that triggered the call. Filled in by the dispatcher. */
18
+ tool?: string | undefined;
19
+ /** Optional workaround hint from src/utils/known-issues.ts. */
20
+ readonly hint?: string | undefined;
21
+ constructor(message: string, status: number, details?: unknown | undefined,
22
+ /** Method + path of the Walmart call, e.g. "GET /v3/returns/count". */
23
+ endpoint?: string | undefined,
24
+ /** MCP tool that triggered the call. Filled in by the dispatcher. */
25
+ tool?: string | undefined,
26
+ /** Optional workaround hint from src/utils/known-issues.ts. */
27
+ hint?: string | undefined);
28
+ /**
29
+ * Serialize to the JSON shape returned to the MCP client. Optional fields
30
+ * are omitted when unset to keep error payloads compact.
31
+ */
32
+ toResponse(): Record<string, unknown>;
33
+ }
34
+ /**
35
+ * Build a human/LLM-readable message from a Walmart error response, preserving
36
+ * as much detail as the body provides:
37
+ * - structured `error[]`/`errors[]` → `CODE: description (field: x)`, joined
38
+ * - otherwise the raw body (JSON or text), so nothing is silently dropped
39
+ * - finally falls back to status + statusText
40
+ */
41
+ export declare function formatWalmartError(status: number, statusText: string, data: unknown): string;
@@ -0,0 +1,97 @@
1
+ /**
2
+ * Error raised for a non-2xx Walmart API response.
3
+ *
4
+ * Carries the HTTP status and the raw response body so callers (and the LLM)
5
+ * get the full Walmart error detail instead of a lossy `"HTTP 404: Not Found"`
6
+ * string. Additional context fields (endpoint / tool / hint) are populated by
7
+ * the request interceptor and the tool dispatcher so the LLM sees:
8
+ * - which Walmart endpoint failed
9
+ * - which MCP tool triggered it
10
+ * - a workaround hint for known-broken Walmart endpoints (Known Issues table)
11
+ */
12
+ export class WalmartApiError extends Error {
13
+ status;
14
+ details;
15
+ endpoint;
16
+ tool;
17
+ hint;
18
+ constructor(message, status, details,
19
+ /** Method + path of the Walmart call, e.g. "GET /v3/returns/count". */
20
+ endpoint,
21
+ /** MCP tool that triggered the call. Filled in by the dispatcher. */
22
+ tool,
23
+ /** Optional workaround hint from src/utils/known-issues.ts. */
24
+ hint) {
25
+ super(message);
26
+ this.status = status;
27
+ this.details = details;
28
+ this.endpoint = endpoint;
29
+ this.tool = tool;
30
+ this.hint = hint;
31
+ this.name = 'WalmartApiError';
32
+ }
33
+ /**
34
+ * Serialize to the JSON shape returned to the MCP client. Optional fields
35
+ * are omitted when unset to keep error payloads compact.
36
+ */
37
+ toResponse() {
38
+ const payload = {
39
+ error: this.message,
40
+ status: this.status,
41
+ };
42
+ if (this.details !== undefined)
43
+ payload.details = this.details;
44
+ if (this.endpoint)
45
+ payload.endpoint = this.endpoint;
46
+ if (this.tool)
47
+ payload.tool = this.tool;
48
+ if (this.hint) {
49
+ payload.hint = this.hint;
50
+ payload.isKnownIssue = true;
51
+ }
52
+ return payload;
53
+ }
54
+ }
55
+ /** Walmart uses both `{ errors: [...] }` and `{ error: [...] }` across services. */
56
+ function extractErrors(data) {
57
+ if (!data || typeof data !== 'object')
58
+ return [];
59
+ const obj = data;
60
+ const raw = obj.errors ?? obj.error;
61
+ if (Array.isArray(raw))
62
+ return raw;
63
+ if (raw && typeof raw === 'object')
64
+ return [raw];
65
+ return [];
66
+ }
67
+ function truncate(s, max) {
68
+ return s.length > max ? `${s.slice(0, max)}…(truncated)` : s;
69
+ }
70
+ /**
71
+ * Build a human/LLM-readable message from a Walmart error response, preserving
72
+ * as much detail as the body provides:
73
+ * - structured `error[]`/`errors[]` → `CODE: description (field: x)`, joined
74
+ * - otherwise the raw body (JSON or text), so nothing is silently dropped
75
+ * - finally falls back to status + statusText
76
+ */
77
+ export function formatWalmartError(status, statusText, data) {
78
+ const entries = extractErrors(data);
79
+ if (entries.length) {
80
+ const parts = entries.map((e) => {
81
+ const code = e.code ? `${e.code}: ` : '';
82
+ const desc = e.description || e.message || e.info || '';
83
+ const field = e.field ? ` (field: ${e.field})` : '';
84
+ return `${code}${desc}${field}`.trim();
85
+ });
86
+ return `HTTP ${status}: ${parts.join('; ')}`;
87
+ }
88
+ if (data && typeof data === 'object') {
89
+ const json = JSON.stringify(data);
90
+ if (json && json !== '{}')
91
+ return `HTTP ${status}: ${truncate(json, 500)}`;
92
+ }
93
+ else if (typeof data === 'string' && data.trim()) {
94
+ return `HTTP ${status}: ${truncate(data.trim(), 500)}`;
95
+ }
96
+ return `HTTP ${status}: ${statusText}`;
97
+ }
@@ -0,0 +1,22 @@
1
+ /**
2
+ * Tiny searchable catalog of Walmart Marketplace endpoint patterns and the
3
+ * dedicated wrapped tools that already cover them. Used by
4
+ * walmart_search_endpoints to suggest "use this existing tool first".
5
+ *
6
+ * Keep this short — it is a discoverability aid, not a full API reference.
7
+ */
8
+ export interface EndpointEntry {
9
+ /** Tags for keyword matching. */
10
+ tags: string[];
11
+ /** "GET /v3/feeds" — human-friendly. */
12
+ signature: string;
13
+ /** Wrapped tool that covers this endpoint, if any. */
14
+ wrappedTool?: string;
15
+ /** One-line description. */
16
+ description: string;
17
+ }
18
+ export declare const ENDPOINT_CATALOG: ReadonlyArray<EndpointEntry>;
19
+ /** Case-insensitive substring + tag-match search. */
20
+ export declare function searchEndpoints(query: string, limit?: number): ReadonlyArray<EndpointEntry & {
21
+ matchScore: number;
22
+ }>;
@@ -0,0 +1,89 @@
1
+ /**
2
+ * Tiny searchable catalog of Walmart Marketplace endpoint patterns and the
3
+ * dedicated wrapped tools that already cover them. Used by
4
+ * walmart_search_endpoints to suggest "use this existing tool first".
5
+ *
6
+ * Keep this short — it is a discoverability aid, not a full API reference.
7
+ */
8
+ export const ENDPOINT_CATALOG = [
9
+ // ---------- Items ----------
10
+ { tags: ['item', 'list', 'catalog'], signature: 'GET /v3/items', wrappedTool: 'walmart_get_all_items', description: 'List items in seller catalog.' },
11
+ { tags: ['item', 'single', 'sku'], signature: 'GET /v3/items/{sku}', wrappedTool: 'walmart_get_item', description: 'Get single item by SKU.' },
12
+ { tags: ['item', 'retire', 'delist'], signature: 'DELETE /v3/items/{sku}', wrappedTool: 'walmart_retire_item', description: 'Retire (unpublish) an item.' },
13
+ { tags: ['taxonomy', 'category'], signature: 'GET /v3/items/taxonomy', wrappedTool: 'walmart_get_taxonomy', description: 'Get Walmart category taxonomy.' },
14
+ { tags: ['spec', 'attribute'], signature: 'GET /v3/items/spec', wrappedTool: 'walmart_get_item_spec', description: 'Get required attributes for a product type.' },
15
+ { tags: ['hazmat', 'onhold'], signature: 'POST /v3/items/onhold/search', wrappedTool: 'walmart_get_hazmat_items', description: 'Search items on hold for hazmat review.' },
16
+ // ---------- Inventory ----------
17
+ { tags: ['inventory', 'stock', 'sku'], signature: 'GET /v3/inventory', wrappedTool: 'walmart_get_inventory', description: 'Get inventory for a SKU.' },
18
+ { tags: ['inventory', 'update', 'stock'], signature: 'PUT /v3/inventory', wrappedTool: 'walmart_update_inventory', description: 'Update inventory for a SKU.' },
19
+ { tags: ['inventory', 'multi-node', 'ship-node'], signature: 'GET /v3/inventories', wrappedTool: 'walmart_get_inventory_all_nodes', description: 'Get inventory across all ship nodes.' },
20
+ { tags: ['lag', 'lag-time'], signature: 'GET /v3/lagtime', wrappedTool: 'walmart_get_lag_time', description: 'Get fulfillment lag time for a SKU.' },
21
+ // ---------- Pricing ----------
22
+ { tags: ['price', 'update', 'base'], signature: 'PUT /v3/price', wrappedTool: 'walmart_update_price', description: 'Update base price for a SKU.' },
23
+ { tags: ['promo', 'promotion', 'sale', 'discount'], signature: 'POST /v3/feeds?feedType=PROMO_PRICE', wrappedTool: 'walmart_submit_promo_price_feed', description: 'Submit a promotional price feed.' },
24
+ { tags: ['repricer', 'buy-box', 'compete'], signature: 'GET /v3/repricer/strategies', wrappedTool: 'walmart_get_repricer_strategies', description: 'List repricer strategies (Pro Seller).' },
25
+ // ---------- Feeds ----------
26
+ { tags: ['feed', 'status'], signature: 'GET /v3/feeds/{feedId}', wrappedTool: 'walmart_get_feed_status', description: 'Get feed processing status.' },
27
+ { tags: ['feed', 'list', 'history'], signature: 'GET /v3/feeds', wrappedTool: 'walmart_get_all_feed_statuses', description: 'List recent feeds.' },
28
+ { tags: ['feed', 'submit'], signature: 'POST /v3/feeds', wrappedTool: 'walmart_submit_inventory_feed', description: 'Submit a bulk feed. Use feed-type-specific tools (walmart_submit_inventory_feed, walmart_submit_item_feed, walmart_submit_promo_price_feed) for strict validation.' },
29
+ // ---------- Orders ----------
30
+ { tags: ['order', 'list'], signature: 'GET /v3/orders', wrappedTool: 'walmart_get_all_orders', description: 'List orders with filters.' },
31
+ { tags: ['order', 'released', 'ready'], signature: 'GET /v3/orders/released', wrappedTool: 'walmart_get_released_orders', description: 'List orders ready for fulfillment.' },
32
+ { tags: ['order', 'single', 'purchase-order'], signature: 'GET /v3/orders/{poId}', wrappedTool: 'walmart_get_order', description: 'Get single order by purchase order ID.' },
33
+ { tags: ['acknowledge', 'ack', 'order'], signature: 'POST /v3/orders/{poId}/acknowledge', wrappedTool: 'walmart_acknowledge_order', description: 'Acknowledge a new order.' },
34
+ { tags: ['ship', 'shipment', 'tracking'], signature: 'POST /v3/orders/{poId}/shipping', wrappedTool: 'walmart_ship_order', description: 'Mark order lines as shipped.' },
35
+ { tags: ['cancel', 'order'], signature: 'POST /v3/orders/{poId}/cancel', wrappedTool: 'walmart_cancel_order', description: 'Cancel order lines.' },
36
+ { tags: ['refund', 'order'], signature: 'POST /v3/orders/{poId}/refund', wrappedTool: 'walmart_refund_order', description: 'Refund order lines (negative amount).' },
37
+ // ---------- Returns ----------
38
+ { tags: ['return', 'list'], signature: 'GET /v3/returns', wrappedTool: 'walmart_get_all_returns', description: 'List returns.' },
39
+ { tags: ['return', 'single'], signature: 'GET /v3/returns/{returnOrderId}', wrappedTool: 'walmart_get_return', description: 'Get single return.' },
40
+ { tags: ['return', 'approve'], signature: 'POST /v3/returns/approve', wrappedTool: 'walmart_approve_return', description: 'Approve a return.' },
41
+ { tags: ['return', 'reject'], signature: 'POST /v3/returns/reject', wrappedTool: 'walmart_reject_return', description: 'Reject a return.' },
42
+ { tags: ['return', 'refund'], signature: 'POST /v3/returns/{rid}/items/{iid}/refund', wrappedTool: 'walmart_issue_return_refund', description: 'Issue refund for a return.' },
43
+ { tags: ['return', 'label', 'shipping'], signature: 'POST /v3/returns/{rid}/items/{iid}/shippinglabel', wrappedTool: 'walmart_generate_return_label', description: 'Generate return shipping label.' },
44
+ // ---------- Reports ----------
45
+ { tags: ['report', 'request', 'generate'], signature: 'POST /v3/reports/reportRequests', wrappedTool: 'walmart_create_report', description: 'Request generation of a report.' },
46
+ { tags: ['report', 'status'], signature: 'GET /v3/reports/reportRequests/{id}', wrappedTool: 'walmart_get_report_status', description: 'Check report generation status.' },
47
+ { tags: ['report', 'download'], signature: 'GET /v3/reports/reportRequests/{id}/download', wrappedTool: 'walmart_download_report', description: 'Download a READY report.' },
48
+ { tags: ['report', 'schedule', 'recurring'], signature: 'POST /v3/reports/reportSchedules', wrappedTool: 'walmart_create_report_schedule', description: 'Create a recurring report schedule.' },
49
+ // ---------- Notifications / Webhooks ----------
50
+ { tags: ['webhook', 'subscription', 'notification'], signature: 'GET /v3/notifications/subscriptions', wrappedTool: 'walmart_get_subscriptions', description: 'List webhook subscriptions.' },
51
+ { tags: ['webhook', 'create'], signature: 'POST /v3/notifications/subscriptions', wrappedTool: 'walmart_create_subscription', description: 'Create a webhook subscription.' },
52
+ // ---------- Insights ----------
53
+ { tags: ['quality', 'listing-quality', 'score'], signature: 'GET /v3/insights/items/listingQuality', wrappedTool: 'walmart_get_listing_quality', description: 'Get store listing quality score.' },
54
+ // ---------- Settings / Partner ----------
55
+ { tags: ['partner', 'seller-info', 'account'], signature: 'GET /v3/partner/info', wrappedTool: 'walmart_get_partner_info', description: 'Get partner account info.' },
56
+ { tags: ['fulfillment-center', 'ship-node'], signature: 'GET /v3/shipping/labels/fulfillmentcenters', wrappedTool: 'walmart_get_fulfillment_centers', description: 'List fulfillment centers.' },
57
+ // ---------- Auth / Diagnostics ----------
58
+ { tags: ['token', 'auth', 'oauth'], signature: 'POST /v3/token', wrappedTool: 'walmart_get_token', description: 'Get OAuth Bearer token.' },
59
+ { tags: ['rate', 'budget', 'limit'], signature: '(internal)', wrappedTool: 'walmart_get_rate_budget', description: 'Snapshot local + server rate-limit state.' },
60
+ ];
61
+ /** Case-insensitive substring + tag-match search. */
62
+ export function searchEndpoints(query, limit = 10) {
63
+ const q = query.toLowerCase().trim();
64
+ if (!q)
65
+ return [];
66
+ const tokens = q.split(/\s+/).filter(Boolean);
67
+ const scored = [];
68
+ for (const entry of ENDPOINT_CATALOG) {
69
+ let score = 0;
70
+ const tagBag = entry.tags.join(' ').toLowerCase();
71
+ const sigBag = entry.signature.toLowerCase();
72
+ const descBag = entry.description.toLowerCase();
73
+ const toolBag = (entry.wrappedTool ?? '').toLowerCase();
74
+ for (const tok of tokens) {
75
+ if (tagBag.includes(tok))
76
+ score += 3;
77
+ if (toolBag.includes(tok))
78
+ score += 2;
79
+ if (sigBag.includes(tok))
80
+ score += 2;
81
+ if (descBag.includes(tok))
82
+ score += 1;
83
+ }
84
+ if (score > 0)
85
+ scored.push({ ...entry, matchScore: score });
86
+ }
87
+ scored.sort((a, b) => b.matchScore - a.matchScore);
88
+ return scored.slice(0, limit);
89
+ }
@@ -0,0 +1,12 @@
1
+ /**
2
+ * Insert or update `KEY=VALUE` pairs in a .env file, preserving the rest of
3
+ * the file. An existing (optionally commented-out) line for a key is replaced
4
+ * in place; otherwise the pair is appended.
5
+ *
6
+ * The replacement uses a *function* form of `String.prototype.replace` so that
7
+ * values containing `$` sequences (e.g. `$1`, `$&`, `$$`) are written literally
8
+ * instead of being interpreted as regex replacement patterns. Walmart access
9
+ * tokens and client secrets are opaque and can contain `$`, which would
10
+ * otherwise corrupt the persisted value and break authentication on restart.
11
+ */
12
+ export declare function upsertEnvVars(updates: Record<string, string>, envPath?: string): void;