Skip to main content
Glama
jumia-vendor-center

jumia-vendor-center

by damurka

jumia-vendor-mcp

An MCP server for Jumia's Vendor Center API (GPM catalog + GOP orders), built against the OpenAPI spec published at https://vendorcenter.jumia.com/api-docs/openapi.yaml (fetched 2026-09-05). Implemented in TypeScript, run directly by Node (no build step).

It exposes the catalog/order operations as MCP tools so an MCP client (Claude Desktop, Claude Code, Cursor, Windsurf, or any other MCP-compatible LLM tool) can call them directly, plus a few heuristic "review list" tools (find_outdated_products, find_duplicate_products, find_variant_fragments) for things the API has no native concept of - read Limitations before you rely on those.

Contents

Related MCP server: lamoda-mcp-ru

Quick start (Claude Code plugin)

claude plugin marketplace add damurka/jumia-vendor-mcp
claude plugin install jumia-vendor-mcp@jumia-vendor-mcp

Then, inside a Claude Code session, run the /plugin configure jumia-vendor-mcp slash command and paste in a Client Id and Refresh Token - see Getting Vendor Center credentials below for where those come from. That's it; skip to Tools for what you can do with it.

Not using Claude Code? See As a standalone MCP server.

Prerequisite

Node.js >= 24 must be installed and on PATH. Every command in this doc runs through it (node ...), including the MCP server itself when launched by a client - there is no separate build/compile step; Node runs the .ts files directly via its native type-stripping support. If Node is missing, the plugin's MCP connection simply fails to start - claude mcp list will show it as not connected rather than hanging silently, which is the first place to look if nothing seems to be working.

If you installed this as a Claude Code plugin and don't know where its files live on disk (e.g. to run npm install below), run claude mcp list - it prints the exact resolved directory each MCP server is running from, regardless of how it was installed. For a plugin installed from a real (non-local-path) marketplace, Claude Code also caches plugin files at a predictable location: ~/.claude/plugins/cache/<marketplace>/<plugin-name>/<version>/.

Installation

As a Claude Code plugin

This repo is itself a Claude Code plugin - .claude-plugin/plugin.json declares the jumia-vendor-center MCP server via ${CLAUDE_PLUGIN_ROOT}, so it works from wherever it's installed.

Install straight from GitHub:

claude plugin marketplace add damurka/jumia-vendor-mcp
claude plugin install jumia-vendor-mcp@jumia-vendor-mcp

Or, if you've cloned it locally instead (e.g. for development), point at the directory:

claude plugin marketplace add /absolute/path/to/jumia-vendor-mcp
claude plugin install jumia-vendor-mcp@jumia-vendor-mcp

Or, for one-off/dev use without installing anything:

claude --plugin-dir /absolute/path/to/jumia-vendor-mcp

Any of the three still need npm install run once in the plugin's own directory first - see the Prerequisite section above if you don't know where that directory is.

Then configure credentials - inside a Claude Code session, run:

/plugin configure jumia-vendor-mcp

and fill in the Client Id and Refresh Token fields it prompts for (get these first from Getting Vendor Center credentials below). This is a slash command run inside a chat session, not a claude plugin ... shell subcommand - the CLI itself has no configure verb. It's powered by plugin.json's userConfig block, and the Refresh Token goes into Claude Code's own secure credential storage, never a plaintext file in this project.

The older node src/setup.ts path (see As a standalone MCP server below) still works too, as an alternative to /plugin configure - it isn't tied to ${CLAUDE_PLUGIN_ROOT} at all, so running it once covers every install of this plugin on that machine, regardless of where it's installed from.

As a standalone MCP server

For Claude Desktop, Cursor, Windsurf, Cline, Zed, or any other MCP-compatible client that isn't plugin-aware:

npm install
node src/setup.ts

node src/setup.ts prompts for a Client Id and a hidden Refresh Token (see Getting Vendor Center credentials below for where to get them), then validates them against the live API immediately - the same pattern as Firebase CLI's firebase login:ci. It stores them in ~/.config/jumia-vendor-mcp/credentials.json, a per-user file outside this project directory, never a project-local .env, so there's nothing here that could ever be accidentally committed. Every person who uses this server runs it once against their own Vendor Center account.

Then register the server directly as a stdio process (adjust the path to wherever you cloned this repo):

{
  "mcpServers": {
    "jumia-vendor-center": {
      "command": "node",
      "args": ["/absolute/path/to/jumia-vendor-mcp/src/server.ts"]
    }
  }
}

Alternative to node src/setup.ts: put JUMIA_CLIENT_ID/ JUMIA_REFRESH_TOKEN directly into that same JSON block's env object, if the client supports one:

{
  "mcpServers": {
    "jumia-vendor-center": {
      "command": "node",
      "args": ["/absolute/path/to/jumia-vendor-mcp/src/server.ts"],
      "env": {
        "JUMIA_CLIENT_ID": "your-client-id",
        "JUMIA_REFRESH_TOKEN": "your-refresh-token"
      }
    }
  }
}

Only do this in a config file that isn't checked into version control - unlike Claude Code's userConfig, this is a plaintext value sitting in a JSON file, not secure storage.

Getting Vendor Center credentials

Both installation paths above need the same two values from your own Vendor Center account:

  1. Register a Self Authorization application: Settings -> Applications -> Create Application -> Self Authorization. Unlike a Web Application, this needs no human present to log in - required for a server that runs unattended/on a schedule.

  2. Use Generate Token on that application to get a Refresh Token.

There's no way to script either step - it's a manual, one-time action in Vendor Center's UI, by design of their platform. Every person who uses this server does this once, in their own account, exactly like firebase login needs a real browser session once.

Non-secret configuration

These are plain environment variables, not stored anywhere - set them if you need to override a default (see src/config.ts's module docstring for the full picture). There is no .env file support at all; these must be real, shell-exported environment variables (or, for a Claude Code plugin install, values Claude Code passes through as env vars).

Variable

Default

Purpose

JUMIA_AUTH_BASE_URL

https://vendor-api.jumia.com

OAuth token endpoint base

JUMIA_API_BASE_URL

https://vendor-api.jumia.com

Vendor Center API base

JUMIA_SHOP_ID

(none)

default shopId for tools that need one and aren't given one explicitly

JUMIA_AUDIT_LOG

./data/audit.log

path to the JSONL audit log of write actions

JUMIA_RATE_LIMIT_RPM

200

requests/minute cap, per Jumia's docs

JUMIA_RATE_LIMIT_RPS

4

requests/second cap, per Jumia's docs

JUMIA_CLIENT_ID / JUMIA_REFRESH_TOKEN

(from stored credentials)

override the stored Client Id/Refresh Token - useful for CI/automation, the same role FIREBASE_TOKEN plays for Firebase CLI

Verifying it works

Run the tests and typecheck:

npm test        # node --test, no separate test-framework install needed
npm run typecheck

Run the server directly to sanity-check it starts:

npm start   # or: node src/server.ts

It talks MCP over stdio and will just sit there waiting for a client - that's expected; Ctrl-C to stop.

After a git pull or any dependency change, run npm install again. Unlike a uv-managed Python project, Node doesn't auto-sync dependencies on every launch - a stale node_modules fails loudly (module-not-found) rather than self-healing.

Tools

Tool

Requirement it maps to

find_outdated_products

1. find outdated products that need to be removed

deactivate_products

2. remove outdated products (see Limitations - this deactivates, doesn't delete; automatically zeroes stock first)

update_products, update_price, update_stock

3. update products

create_products

4. create new products, including images and all documented fields

sync_products

5. keep products up to date (diffs a desired state against live data, pushes only what changed)

find_duplicate_products

6. merge products posted as different products (see Limitations - reports candidates, doesn't merge)

find_variant_fragments, merge_variant_fragments

6b. the same real item posted as a separate product per color instead of one product with a color variation - detects candidate clusters, then builds (but does not submit) the consolidated create/deactivate payload

check_content_policy

pre-flight scan against phrases already confirmed to trip Jumia's word blacklist; create_products/update_products run this automatically and block on a match

list_orders, get_order_items, cancel_order_items

7. manage orders

print_shipping_labels, pack_orders(_v2), mark_ready_to_ship, get_shipment_providers

8. print labels / fulfillment

list_shops, list_brands, list_categories, get_attribute_set, list_products, get_stock, get_feed_status, create_consignment, update_consignment, get_consignment_stock, get_payout_statements

reference data, warehouse inbound stock, payouts, and polling async feed results

Every write tool (create/update/deactivate/cancel/pack/etc) appends a line to a local JSONL audit log (JUMIA_AUDIT_LOG, default ./data/audit.log) before returning - {ts, action, request, result, ok, error} per call. Given how much of this is one-way (see below), that trail is worth keeping.

Limitations (read before trusting the automation)

Structural gaps in the API itself

No delete, only deactivate. The published API has no endpoint to delete a product. status can only be set to ACTIVE/INACTIVE by a seller; DELETED shows up as a read-only value on list_products - only Jumia's own catalog ops can actually remove a listing. deactivate_products sets INACTIVE; treat any request to "delete" or "remove" a product as a request to deactivate it, and tell whoever's asking that a true delete needs a request to Jumia (account manager / catalog support), not an API call.

No merge. There's no endpoint to merge two listings of the same real product (which would need to consolidate reviews, ranking history, and stock). find_duplicate_products only detects likely duplicates (GTIN match, or brand+category+images+fuzzy-name match) and suggests which one to keep - resolving it is still "review the list, then deactivate the ones you're dropping," done by a person.

Only the mutable fields are actually mutable. Per the docs' own table: update_products can change additional category, brand, config attributes, GTIN barcode, simple attributes, and variation - it explicitly cannot change the main image, main category, or parent SKU (and price/initial stock go through the separate update_price/update_stock feeds, not this one). If "keep products up to date" means fixing a wrong main image or category on an existing listing, there's no API for that at all - it has to be recreated, or handled by Jumia support.

No cancellation-reason field. cancel_order_items's schema is just a list of order item IDs - no reason code, no comment. If you need that for SLA/audit reporting, capture it in your own system when you call the tool; the audit log records who/when, not why.

No product-level "last sold" query. get_sales_order_item looks up one specific order item by ID, not "when did this SKU last sell" - to build that you'd page through list_orders/get_order_items yourself and join on SKU, which is expensive across a large order history. Not wired into find_outdated_products for that reason; if you need it, it's a natural next heuristic to add once you've decided how far back "recent" means.

Caveats specific to this project's own heuristics

"Outdated" and "duplicate" are both heuristics we invented, not Jumia concepts - see src/heuristics.ts's module docstring for exactly what signals they use and why. Tune the grace-period parameters (or add your own rule) to match your catalog; don't treat the default thresholds as authoritative.

find_variant_fragments is domain-informed, not universal. It clusters by (brand, model, case-type) extracted from the product name via patterns seeded from a real catalog of ~700 phone-case listings - see heuristics.ts's BRAND_PATTERNS/MODEL_PATTERNS/CASE_TYPE_PATTERNS if you need to extend it for another product category. Its flags on a cluster (price outlier, bundle/different-material keywords, weight-unit anomaly) are prompts to go read that listing's actual description, not proof of a real problem - they fire on marketing copy too (e.g. "attaches to MagSafe wallets" flags as a wallet-material mention). merge_variant_fragments never calls create_products/deactivate_products itself - it only builds the payload, so every write still goes through the normal, visible, audited tool calls.

check_content_policy's blacklist is only what's failed live so far, not Jumia's actual (unpublished) word blacklist - currently just one confirmed phrase ("screen protection"). A clean scan means "hasn't failed this way before," not "guaranteed to pass" - create_products/ update_products still surface Jumia's real validation error for anything not yet on the list.

API behavior that disagrees with its own docs

Confirmed against a live account:

  • product.name on GET /catalog/products is a plain string, not the documented {"value": ...} object - src/heuristics.ts matches the live shape.

  • The create-product schema types brand.code/category.code as number, but the docs' own changelog says the live API actually returns/expects strings - confirmed live too.

  • create_products' parentSku is documented as optional but is actually required - omitting it on a standalone product fails with "Required field [Product.ParentSKU] is missing or null." For a non-variant listing, just set it equal to sellerSku.

  • deactivate_products/update_stock/update_price need the variation id (variations[].id from GET /catalog/products), not the top-level product-set id - passing the product-set id fails with "Product by Sid [...] not found." find_outdated_products rows already carry the right one as variation_id; a raw list_products read does not make this distinction obvious.

  • print_shipping_labels's label field has no documented shape (raw bytes? base64? a URL?) - inspect a real response before building anything downstream that assumes one.

  • GET /catalog/products?status=INACTIVE hangs/times out server-side - confirmed with a raw fetch bypassing this project's own client entirely, so it's a live API issue, not a bug here. status=ACTIVE and an unfiltered list both work fine. Workaround: page through the full catalog with no status filter and check each variation's businessClient status client-side instead of asking the API to filter by INACTIVE for you.

  • GET /orders/items returns a JSON array of {orderId, orderNumber, items} objects, not a bare object - easy to miss since a single-order query returns a one-element array that looks like it could be the object itself.

Operational notes

Rate limits are enforced per Mastershop (200 requests/minute, capped at 4/second) - src/http.ts's rate limiter paces every call against that, but if you run multiple instances of this server against the same Mastershop simultaneously, they don't share state and can collectively blow past it.

Not covered at all, because the published API doesn't expose it: returns and refunds, reviews/ratings, competitor/buybox price monitoring, tax and duties compliance, and content-score/SEO optimization of listings (there's a content guideline worth following manually when writing product copy, but nothing in the API scores or validates it for you).

Repo layout

src/
  util/mutex.ts      - promise-chaining async mutex (no built-in JS equivalent of asyncio.Lock)
  credentials.ts     - per-user credential file (Firebase-CLI style), outside the project
  setup.ts           - `node src/setup.ts`, the one-time interactive login (CLI path; `/plugin
                       configure jumia-vendor-mcp` is the other, via plugin.json's userConfig)
  config.ts          - env/config loading
  auth.ts            - OAuth2 refresh-token handling, with rotation persisted via credentials.ts
  http.ts            - rate limiting, retry/backoff, per-service error-shape normalization
  stringSimilarity.ts - a from-scratch, verified-against-Python port of difflib's ratio()
  client.ts          - one method per documented endpoint
  heuristics.ts      - "outdated" / "duplicate" / "variant fragment" detection + merge-payload
                       building + content-policy scanning (pure, unit-tested)
  audit.ts           - append-only JSONL write-action log
  server.ts          - the actual MCP tool definitions
tests/
  heuristics.test.ts    - heuristics, no network
  client.test.ts        - client.ts against a fake HTTP layer (checks paths/payloads)
  configAndAuth.test.ts - credential file precedence + rotation persistence, no real file/network
  serverSmoke.test.ts   - server imports cleanly, every tool registers

Run with node directly (Node >= 24's native TypeScript type-stripping) - no dist/, no tsc build step. npm run typecheck (a tsc --noEmit pass) is separate and only checks types; it doesn't produce runnable output.

Available Tools

27 tools
cancel_order_itemsA

Cancel one or more order items. Requires the VC - Order Manager role on the calling application/user. No cancellation-reason field exists in this endpoint's schema - the audit log records who/when this tool was called, but not a business reason, so capture that elsewhere if you need it for SLA reporting.

Inputs: order_item_ids (required).

create_consignmentA

Create a consignment (inbound stock shipment to a Jumia warehouse). products: [{"sku": "...", "quantity": 10, "labelCode": "..."}]. shipping_date format is 'YYYY-MM-DD HH:mm:ss' (not ISO-8601, despite looking like it). Returns {purchaseOrderNumber}.

Inputs: shop_id (required), products (required), shipping_date (required), business_client_code (required), +1 more.

create_productsA

Create new products (async feed). Poll the returned feedId with get_feed_status() until status is COMPLETED, then call it again (or list_products by sellerSku) to learn each product's real productSid and QC status - both are required before you can update stock, price or status on a newly-created product.

Each item in products (per the published schema): name: {"value": "...", "translations": [{"language": "en", "value": "..."}]} description: {"value": "...", "translations": [...]} sellerSku: str (required, your own unique SKU) parentSku: str (REQUIRED, despite the published schema marking it optional - confirmed live: omitting it on a standalone, non-variant product fails with "Required field [Product.ParentSKU] is missing or null." For a single listing with no size/color variants, just set this equal to sellerSku. Only set it to something else when you actually want to group size/color variants together - every product sharing a parentSku must then pass the SAME images.) variation: str (required if parentSku groups variants; for a standalone product, set it equal to sellerSku/name too) brand: {"code": ..., "name": "..."} category: {"code": ..., "name": "..."} (from list_categories) images: [{"url": "https://...", "primary": true}, ...] (>= 1 primary required) price: {"currency": "NGN", "value": 12000, "salePrice": {"value": 9000, "startAt": "2026-09-10", "endAt": "2026-09-20"}} stock: 50 attributes: [{"name": "color", "value": "Black"}, ...] (from get_attribute_set - call it first to see which attributes this category marks mandatory, e.g. product_weight/short_description are required for AC Chargers) businessClients: [{"businessClientCode": "jumia-ng", "price": {...}}, ...] (needed for a global/multi-country seller selling in local currency)

Before calling this for a real-world branded product, SEARCH for the manufacturer's actual spec sheet, description copy, and product image URLs (their regional store site) rather than inventing name/description/spec/image content - Jumia's own content guidelines expect accurate listings, and a fabricated spec (wrong wattage, invented weight, wrong included accessories) risks a QC rejection or a listing that doesn't match what ships. If the manufacturer's site blocks a plain fetch (403), a real browser session (e.g. claude-in-chrome) often gets through where a headless fetch doesn't. Only fields you truly cannot find published anywhere (e.g. shipping weight) should be flagged to the user as an unverified estimate rather than silently guessed.

Cap ~1000 products per call - this tool does not auto-chunk larger lists for you (chunk them yourself and call this repeatedly, tracking each feedId, so a failure in batch 6 doesn't force you to redo 1-5).

Inputs: shop_id (required), products (required).

deactivate_productsA

The closest thing to "removing" a product from Jumia: sets status to INACTIVE per business client. THIS DOES NOT DELETE THE LISTING - there is no delete endpoint in the published API; INACTIVE just makes it unsellable/hidden. If you actually need a listing permanently gone, that's a request to your Jumia account manager, not something this tool (or any seller-facing API call) can do.

products: [{"id": "<productSid, i.e. variation_id>", "sellerSku": "...", "business_client_codes": ["jumia-ng", ...]}] (accepts a singular "business_client_code" string too, for convenience when acting on one find_outdated_products listing at a time - those rows already have "variation_id"/"seller_sku"/"business_client_code" under exactly those names, just rename variation_id -> id).

Logs every call to the local audit log before returning.

Inputs: products (required).

find_duplicate_productsA

Flag products that look like the same real-world item listed more than once: exact GTIN/EAN/barcode match, or same brand+category+images with a near-identical name. Jumia's seller API has NO merge endpoint, so this only reports clusters with a suggested canonical listing (live somewhere - ACTIVE + QC APPROVED on any business client - then oldest wins) - resolving it means you decide, then call deactivate_products() on the ones you're dropping. Narrow with category_code for large catalogs; this does a full paginated scan which gets expensive across an entire multi-country catalog.

Inputs: shop_id, category_code, max_products_scanned, name_similarity_threshold.

find_outdated_productsA

Scan the catalog for products that look outdated: QC-rejected and never fixed, ACTIVE with zero stock for a long time, or ACTIVE and untouched for a very long time. This is a HEURISTIC - the Vendor Center API has no "outdated" concept - so treat the result as a review list, not an automatic deletion queue. Nothing is changed by calling this; pair it with deactivate_products() after a human (or you, deliberately) has looked at the list.

Returns {scanned, flagged: [{listing, reasons}], truncated}. Each listing is a flattened (variation, businessClient) row that already carries variation_id (== productSid), seller_sku and business_client_code - i.e. exactly what deactivate_products needs, with no extra lookup required.

Inputs: status, shop_id, qc_status, category_code, +4 more.

get_attribute_setA

List the attributes (required or not, allowed values/options, validation rules) for a category's attribute set. Get attribute_set_id from list_categories()'s attributeSet.sid field.

Inputs: attribute_set_id (required).

get_consignment_stockB

Check received/quarantined/defective/canceled/returned/failed counts for stock sent to a Jumia warehouse.

Inputs: sku (required), business_client_code (required).

get_feed_statusA

Poll an async feed (returned by create_products/update_products/update_price/update_stock/deactivate_products) until status is COMPLETED or FAILED. For a PRODUCT_CREATION feed, this is also where you get each new product's productSid and QC status.

Inputs: feed_id (required).

get_order_itemsC

GET /orders/items for a specific order.

Inputs: order_id (required), status, shop_id.

get_payout_statementsB

List payout statements (for reconciling what Jumia has paid out against your own books). NOT financial/tax advice - just the raw statement data.

Inputs: page, paid, size, country, +2 more.

get_shipment_providersA

List shipment providers available for an order item, including whether each requires a caller-supplied tracking code (use pack_orders_v2 if so).

Inputs: order_item_id (required).

get_stockC

One page of GET /catalog/stock.

Inputs: size, token, product_sids.

list_brandsA

List brand codes/names known to the catalog (paginated).

Inputs: page.

list_categoriesA

List categories. Each category includes attributeSet.sid, which you need before create_products/update_products for a product in that category - pass it to get_attribute_set to see required/optional attributes and their allowed values.

Inputs: page, size, attribute_set_name.

list_ordersA

One page of GET /orders. status/country accept comma-separated lists; omit status to get every status (there's no "ALL" value). Valid country codes: CI, DZ, EG, GH, KE, MA, NG, SN, TN, UG, ZA.

Inputs: size, token, status, country, +3 more.

list_productsB

One page of GET /catalog/products with the documented filters. Use token from the previous response to get the next page.

Inputs: size, token, status, shop_id, +3 more.

list_shopsA

List every shop under the authenticated Vendor Center account.

Inputs: no named parameters.

mark_ready_to_shipB

Mark packed order items ready to ship.

Inputs: order_item_ids (required).

pack_ordersA

Pack order items (v1). order_items: [{"id": "", "shipmentProviderId": "..."}]. Use pack_orders_v2 instead for any provider where get_shipment_providers reports trackingCodeRequired=true.

Inputs: order_items (required).

pack_orders_v2A

Pack order items (v2) - required when the shipment provider needs a caller-supplied tracking code. packages: [{"orderItems": [...], "shipmentProviderId": "...", "trackingCode": "..."}].

Inputs: packages (required).

sync_productsA

Reconcile your source of truth (an ERP export, a spreadsheet you've already parsed to JSON, etc) against what's live on Jumia right now, and push only the fields that actually changed - instead of you hand-writing separate create/update/price/stock calls.

desired: [{"sellerSku": "...", "price": 12000, "currency": "NGN", "stock": 50, "status": "ACTIVE"}, ...] (extend with brand/category/attributes if you also want update_products diffing - this baseline covers the highest-churn fields: price, stock, status.)

Looks up each sellerSku via list_products, diffs against desired, and by default (dry_run=true) returns the planned actions WITHOUT calling anything - review the plan first. Set dry_run=false to actually submit the price/stock/status feeds (batched, respecting the documented ~1000-item-per-feed cap) and get back the resulting feedIds.

Returns {matched, not_found: [sellerSku...], plan: {price: [...], stock: [...], status: [...]}, feed_ids: {...} (only when dry_run=false)}.

Inputs: desired (required), dry_run, shop_id.

update_consignmentC

Update a consignment's shipping status. Dates are 'yyyy-MM-dd'.

Inputs: purchase_order_number (required), is_shipped, name_of_3pl, tracking_number, +3 more.

update_priceB

Update price (async feed). Each item: {"sellerSku", "id", "category", "price": {"currency", "value", "salePrice": {"value","startAt","endAt"}}, "businessClients": [...]}. To clear a sale price, send salePrice's value/startAt/endAt as null rather than omitting salePrice entirely.

Inputs: products (required).

update_productsA

Update the MUTABLE subset of product fields (async feed): additional category, brand, config attributes, GTIN barcode, simple attributes, variation. This CANNOT change the main image, main category, parent SKU, price, or initial stock - use update_price / update_stock for price and stock, and be aware main image/category/parent SKU aren't changeable via this API at all once a product is created.

Each item needs the product's id (productSid) plus whichever fields you're changing.

Inputs: products (required).

update_stockA

Update stock (async feed). Each item: {"sellerSku", "id", "stock"}.

Inputs: products (required).

Tool Schema Changelog

Recent tool additions, removals, and schema changes observed during successful MCP inspections.

Loading tool schema changelog…

    TDQS

    A3.5/5.0

    Scored across 27 tools

    Disambiguation4/5

    Most tools map cleanly to distinct resource+action pairs, with the update_products/update_price/update_stock boundaries explicitly carved out. The main overlap risk is pack_orders vs pack_orders_v2, though the versioned descriptions and get_shipment_providers guidance largely disambiguate them. The two find_* heuristic tools share a style but target clearly different outcomes (duplicates vs outdated).

    Naming Consistency4/5

    The set follows a strong snake_case verb_noun convention throughout (list_*, get_*, create_*, update_*, find_*, deactivate_*). Minor deviations include the pack_orders_v2 version suffix and an inconsistent get_/list_ split between similar read operations (list_orders vs get_order_items). Overall the pattern is predictable enough for an agent to guess tool names.

    Tool Count4/5

    At 27 tools the server is on the heavy side, but it spans multiple distinct sub-domains — product catalog, order fulfillment, consignments, and payouts — making the per-domain count reasonable. Each tool earns its place with a genuine distinct operation rather than redundant variants, aside from the pack_orders v1/v2 pair.

    Completeness4/5

    Product lifecycle coverage is strong: create, list, update mutable fields, update price/stock, deactivate, plus duplicate/outdated heuristics and a sync orchestration tool. Order fulfillment covers pack, label, ready-to-ship, and cancel, but there is no returns/refunds surface. Consignment support has create/update/stock-check but no way to list or fetch a single consignment, a workable minor gap.

    Maintenance

    ActivityStale
    ResponsivenessNo recent community issues

    Related MCP Connectors

    Related MCP Servers

    • A
      license
      Not graded
      quality
      Not graded
      maintenance
      Exposes Amazon Selling Partner API tools for sellers to manage orders, inventory, listings, pricing, analytics, and reports via natural language.
      14 npm
      1
      AGPL 3.0
    • A
      license
      Not graded
      quality
      F
      maintenance
      Enables Lamoda sellers to manage their store via natural language through a MCP server that connects to the official Lamoda Seller API, supporting 155 methods for products, prices, orders, shipments, and more.
      MIT
    • A
      license
      Not graded
      quality
      C
      maintenance
      Enables managing SumUp accounts (catalog, stock, sales, payouts) via natural language in MCP clients, accessing both the public API and undocumented dashboard endpoints.
      MIT