ZingaShop

Generic Resources

Beyond the purpose-built endpoints, the API exposes a large set of catalog,
marketing, shipping and store-configuration objects through a uniform
list / read / create / update / delete pattern at /{resource}. Learn it once
and it works the same for every resource in the table below.

Requires data:read to read and data:write:* to write.

The pattern

Method Path Purpose
GET /papi/v1/{resource} List (supports limit, offset, q, filters, websiteId)
GET /papi/v1/{resource}/{id} Read one
POST /papi/v1/{resource} Create
PATCH /papi/v1/{resource}/{id} Update
DELETE /papi/v1/{resource}/{id} Delete (soft-delete where supported)

List responses use the standard { data, total, limit, offset } envelope. A
delete returns { "deleted": true, "id": "…" }. As everywhere, responses carry
each field in both camelCase and snake_case (see Conventions).

# List the ten most recent promotions
curl "https://api-v1.zingasuite.com/papi/v1/promotions?limit=10" \
  -H "Authorization: Bearer zk_live_xxx"

Available resources

Group Resources
Catalog tags, collections, attribute-sets, attributes, brands
Storefront config currencies, languages, tax-zones, tax-rates
Customers customers, customer-groups, reviews
Marketing & content promotions, coupons, gift-cards, cms-pages, blog-categories, blog-posts, banners, notices, menus
Pricing pricelists
Subscriptions subscription-plans, subscriptions
Digital goods digital-assets, entitlements
Inventory & sales warehouses, returns
Shipping shipping-zones, shipping-methods
Search search-synonyms, search-redirects
URLs url-redirects
Carriers carrier-integrations
Payments payment-gateways

products, orders, inventory and websites have their own purpose-built
endpoints — use those pages, not the generic layer. Calling the generic layer
for one of them returns use_dedicated_endpoint:<resource>.

What each field accepts

The exact create/update fields differ per resource. To discover them, read one
existing row (GET /{resource}/{id}) and mirror its field names in your
request — every readable field name is a valid input name (in camelCase or
snake_case).

Notices

notices is worth a note because two of its fields are lists of ids rather than
scalars, and one is meaningfully nullable:

  • scope is website, category or product — what the notice is attached to.
  • categoryIds / productIds are the targets for the matching scope. Send the
    full list; it replaces what was there.
  • placementsJson is the list of places it draws: site_top, product,
    category, cart, checkout, blog.
  • websiteId is nullable, and null means every storefront on the
    account. Listing with ?websiteId= returns that storefront's notices plus the
    account-wide ones, since both apply to it.
  • startsAt / endsAt are ISO-8601 timestamps, both optional.
  • overridesInherited makes this notice replace the less specific ones instead
    of stacking with them. It is ignored on a website-scoped notice.
# A seasonal notice on twelve products, live for six weeks
curl -X POST "https://api-v1.zingasuite.com/papi/v1/notices" \
  -H "Authorization: Bearer zk_live_xxx" \
  -H "Content-Type: application/json" \
  -d '{
        "name": "Post-monsoon paint care",
        "websiteId": "<storefront-id>",
        "scope": "product",
        "productIds": ["<product-id>", "…"],
        "placementsJson": ["product"],
        "style": "seasonal",
        "title": "Post-monsoon paint care.",
        "body": "Weeks of rain leave water spots and road film on the clear coat.",
        "linkLabel": "Shop paint care",
        "linkUrl": "/paint-care",
        "startsAt": "2026-09-15T00:00:00Z",
        "endsAt": "2026-10-31T00:00:00Z"
      }'

A save that could never render is rejected rather than stored — a notice scoped
to products but placed only in the cart returns scope_needs_a_page_placement,
since the cart has no product to match against.

Operations that aren't available

Some resources are read-only over the API, or are created only through a
dedicated flow (typically because they handle secrets or need side effects).
Attempting an unavailable operation returns a clear 405:

  • resource_not_creatable — this resource can't be created via the API.
  • resource_not_updatable — this resource can't be updated via the API.

Resources that hold credentials or secrets (for example payment-gateways and
carrier-integrations) never return those secrets in responses and can't be
created through the generic layer — configure them in the console.

Was this helpful?