{"openapi":"3.1.0","info":{"title":"Klatchit Public API","version":"1.0.0","description":"Unauthenticated access to the public Klatchit catalog — the same data an anonymous shopper can see on the site: purchasable products, public prices and offers, and the active category tree. No API key is required. Money is always integer minor units (`*_cents`, USD). Responses are `{ data, meta }` and are shared-cacheable; requests are rate limited per client IP.\n\nThe catalog endpoints are read-only. The one exception, POST /cart-links, still cannot buy anything: it mints a link for a HUMAN to open, which prefills that person's own cart for them to review and check out themselves. There is no endpoint that places an order or takes a payment on a shopper's behalf."},"servers":[{"url":"/api/public/v1"}],"tags":[{"name":"Catalog"},{"name":"Cart"}],"paths":{"/search":{"get":{"tags":["Catalog"],"summary":"Search the public catalog","description":"Full-text + faceted product search over purchasable offers. Identical ranking, filtering, and facet counts to the site's own /search page. Each result carries an absolute product-detail URL (`/p/{slug}`) you can fetch via GET /products/{slug}.","parameters":[{"name":"q","in":"query","schema":{"type":"string","maxLength":200},"description":"Free-text query; omit to browse."},{"name":"category","in":"query","schema":{"type":"string"},"description":"Category slug; scopes the search to that subtree."},{"name":"brand","in":"query","style":"form","explode":true,"schema":{"type":"array","items":{"type":"string"}},"description":"Brand slugs. Repeatable, or comma-separated."},{"name":"condition","in":"query","style":"form","explode":true,"schema":{"type":"array","items":{"type":"string","enum":["new","like_new","very_good","good","acceptable","refurbished","used","for_parts"]}},"description":"Offer conditions. Repeatable, or comma-separated."},{"name":"price_min_cents","in":"query","schema":{"type":"integer","minimum":0}},{"name":"price_max_cents","in":"query","schema":{"type":"integer","minimum":0}},{"name":"sort","in":"query","schema":{"type":"string","enum":["relevance","price_asc","price_desc","newest"],"default":"relevance"}},{"name":"page","in":"query","schema":{"type":"integer","minimum":1,"maximum":500,"default":1}},{"name":"page_size","in":"query","schema":{"type":"integer","minimum":1,"maximum":60,"default":24},"description":"Results per page. Values above 60 are clamped, not rejected; the effective value is echoed in meta.page_size."}],"responses":{"200":{"description":"A page of product cards plus facet counts.","content":{"application/json":{"schema":{"$schema":"https://json-schema.org/draft/2020-12/schema","type":"object","properties":{"data":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string"},"slug":{"type":"string"},"title":{"type":"string"},"url":{"type":"string"},"image_url":{"anyOf":[{"type":"string"},{"type":"null"}]},"brand":{"anyOf":[{"type":"object","properties":{"slug":{"anyOf":[{"type":"string"},{"type":"null"}]},"name":{"type":"string"}},"required":["slug","name"],"additionalProperties":false},{"type":"null"}]},"category_breadcrumb":{"type":"array","items":{"type":"object","properties":{"slug":{"type":"string"},"name":{"type":"string"}},"required":["slug","name"],"additionalProperties":false}},"min_price_cents":{"anyOf":[{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991},{"type":"null"}]},"currency":{"type":"string"},"offer_count":{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991},"rating_avg":{"anyOf":[{"type":"number"},{"type":"null"}]},"rating_count":{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991}},"required":["id","slug","title","url","image_url","brand","category_breadcrumb","min_price_cents","currency","offer_count","rating_avg","rating_count"],"additionalProperties":false}},"meta":{"type":"object","properties":{"page":{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991},"page_size":{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991},"total":{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991},"page_count":{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991},"facets":{"type":"object","properties":{"category":{"type":"array","items":{"type":"object","properties":{"value":{"type":"string"},"label":{"type":"string"},"count":{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991}},"required":["value","label","count"],"additionalProperties":false}},"brand":{"type":"array","items":{"type":"object","properties":{"value":{"type":"string"},"label":{"type":"string"},"count":{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991}},"required":["value","label","count"],"additionalProperties":false}},"condition":{"type":"array","items":{"type":"object","properties":{"value":{"type":"string"},"label":{"type":"string"},"count":{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991}},"required":["value","label","count"],"additionalProperties":false}},"price":{"type":"array","items":{"type":"object","properties":{"value":{"type":"string"},"label":{"type":"string"},"count":{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991}},"required":["value","label","count"],"additionalProperties":false}}},"required":["category","brand","condition","price"],"additionalProperties":false},"request_id":{"type":"string"}},"required":["page","page_size","total","page_count","facets","request_id"],"additionalProperties":false}},"required":["data","meta"],"additionalProperties":false}}}},"400":{"$ref":"#/components/responses/Error"},"429":{"$ref":"#/components/responses/RateLimited"},"default":{"$ref":"#/components/responses/Error"}}}},"/products/{slug}":{"get":{"tags":["Catalog"],"summary":"Retrieve a product and its purchasable offers","description":"The full public product record: attributes, images, brand, GTIN/MPN, category breadcrumb, and every currently purchasable offer (cheapest first) with the buy-box winner identified. Inventory depth is never exposed — an offer reports a boolean `in_stock`. A product that is not publicly listed returns 404.","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string"},"description":"The product slug, as it appears in /p/{slug}."}],"responses":{"200":{"description":"The product.","content":{"application/json":{"schema":{"$schema":"https://json-schema.org/draft/2020-12/schema","type":"object","properties":{"data":{"type":"object","properties":{"id":{"type":"string"},"slug":{"type":"string"},"title":{"type":"string"},"description":{"anyOf":[{"type":"string"},{"type":"null"}]},"url":{"type":"string"},"brand":{"anyOf":[{"type":"object","properties":{"slug":{"anyOf":[{"type":"string"},{"type":"null"}]},"name":{"type":"string"}},"required":["slug","name"],"additionalProperties":false},{"type":"null"}]},"category_breadcrumb":{"type":"array","items":{"type":"object","properties":{"slug":{"type":"string"},"name":{"type":"string"}},"required":["slug","name"],"additionalProperties":false}},"gtin":{"anyOf":[{"type":"string"},{"type":"null"}]},"mpn":{"anyOf":[{"type":"string"},{"type":"null"}]},"attributes":{"type":"object","propertyNames":{"type":"string"},"additionalProperties":{}},"images":{"type":"array","items":{"type":"object","properties":{"url":{"type":"string"},"alt":{"anyOf":[{"type":"string"},{"type":"null"}]},"width":{"anyOf":[{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991},{"type":"null"}]},"height":{"anyOf":[{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991},{"type":"null"}]}},"required":["url","alt","width","height"],"additionalProperties":false}},"rating_avg":{"anyOf":[{"type":"number"},{"type":"null"}]},"rating_count":{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991},"currency":{"type":"string"},"min_price_cents":{"anyOf":[{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991},{"type":"null"}]},"offers":{"type":"array","items":{"type":"object","properties":{"listing_id":{"type":"string"},"price_cents":{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991},"list_price_cents":{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991},"currency":{"type":"string"},"condition":{"type":"string","enum":["new","like_new","very_good","good","acceptable","refurbished","used","for_parts"]},"condition_label":{"type":"string"},"store_name":{"type":"string"},"store_slug":{"type":"string"},"in_stock":{"type":"boolean"},"on_sale":{"type":"boolean"}},"required":["listing_id","price_cents","list_price_cents","currency","condition","condition_label","store_name","store_slug","in_stock","on_sale"],"additionalProperties":false}},"buy_box_listing_id":{"anyOf":[{"type":"string"},{"type":"null"}]}},"required":["id","slug","title","description","url","brand","category_breadcrumb","gtin","mpn","attributes","images","rating_avg","rating_count","currency","min_price_cents","offers","buy_box_listing_id"],"additionalProperties":false},"meta":{"type":"object","properties":{"request_id":{"type":"string"}},"required":["request_id"],"additionalProperties":false}},"required":["data","meta"],"additionalProperties":false}}}},"404":{"$ref":"#/components/responses/Error"},"429":{"$ref":"#/components/responses/RateLimited"},"default":{"$ref":"#/components/responses/Error"}}}},"/categories":{"get":{"tags":["Catalog"],"summary":"Retrieve the active category tree","description":"Every active category as a nested tree. Use a node's `slug` as the `category` parameter on /search; `path` is the materialised ltree path (e.g. `electronics.audio.headphones`).","responses":{"200":{"description":"The category tree.","content":{"application/json":{"schema":{"$schema":"https://json-schema.org/draft/2020-12/schema","type":"object","properties":{"data":{"type":"array","items":{"$ref":"#/$defs/__schema0"}},"meta":{"type":"object","properties":{"count":{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991},"request_id":{"type":"string"}},"required":["count","request_id"],"additionalProperties":false}},"required":["data","meta"],"additionalProperties":false,"$defs":{"__schema0":{"type":"object","properties":{"slug":{"type":"string"},"name":{"type":"string"},"path":{"type":"string"},"children":{"type":"array","items":{"$ref":"#/$defs/__schema0"}}},"required":["slug","name","path","children"],"additionalProperties":false}}}}}},"429":{"$ref":"#/components/responses/RateLimited"},"default":{"$ref":"#/components/responses/Error"}}}},"/cart-links":{"post":{"tags":["Cart"],"summary":"Create a cart link for a human to open","description":"Mint a short-lived link that puts specific offers into the cart of whoever OPENS it. This is a handoff, not a purchase: it takes no payment, places no order, reserves no stock, and creates no cart on our side — it returns a URL for a person to open in their own browser, where the items appear in their own cart to review and check out themselves. There is no API for buying on a shopper's behalf.\n\nIdentify each line by the `listing_id` of one offer from GET /products/{slug} (a listing_id picks one seller's offer, not the product). Quantities are 1-99 and up to 20 lines; a repeated listing_id has its quantities summed. Lines that are not purchasable right now are dropped and reported in `rejected` — a generic reason only. If nothing is purchasable the response is a 400 whose error object carries the same `rejected` list. The link expires in 7 days, and price and availability are re-checked when it is opened, so nothing here is a price guarantee. Responses are never cached.","requestBody":{"required":true,"content":{"application/json":{"schema":{"$schema":"https://json-schema.org/draft/2020-12/schema","type":"object","properties":{"items":{"minItems":1,"maxItems":20,"type":"array","items":{"type":"object","properties":{"listing_id":{"type":"string","format":"uuid","pattern":"^([0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[1-8][0-9a-fA-F]{3}-[89abAB][0-9a-fA-F]{3}-[0-9a-fA-F]{12}|00000000-0000-0000-0000-000000000000|ffffffff-ffff-ffff-ffff-ffffffffffff)$"},"quantity":{"type":"integer","minimum":1,"maximum":99}},"required":["listing_id","quantity"]},"description":"Listings to prefill, 1-20 lines."}},"required":["items"]}}}},"responses":{"200":{"description":"The cart link.","content":{"application/json":{"schema":{"$schema":"https://json-schema.org/draft/2020-12/schema","type":"object","properties":{"data":{"type":"object","properties":{"url":{"type":"string"},"expires_at":{"type":"string"},"accepted":{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991},"rejected":{"type":"array","items":{"type":"object","properties":{"listing_id":{"type":"string"},"reason":{"type":"string","enum":["unavailable","insufficient_stock"]}},"required":["listing_id","reason"],"additionalProperties":false}}},"required":["url","expires_at","accepted","rejected"],"additionalProperties":false},"meta":{"type":"object","properties":{"request_id":{"type":"string"}},"required":["request_id"],"additionalProperties":false}},"required":["data","meta"],"additionalProperties":false}}}},"400":{"$ref":"#/components/responses/Error"},"429":{"$ref":"#/components/responses/RateLimited"},"default":{"$ref":"#/components/responses/Error"}}}}},"components":{"schemas":{"Error":{"type":"object","properties":{"error":{"type":"object","properties":{"type":{"type":"string"},"code":{"type":"string"},"message":{"type":"string"},"param":{"type":"string"},"request_id":{"type":"string"}},"required":["type","code","message","request_id"]}},"required":["error"]}},"responses":{"Error":{"description":"Error envelope.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"RateLimited":{"description":"Too many requests from this client. Retry after the number of seconds in the `Retry-After` header.","headers":{"Retry-After":{"schema":{"type":"integer"}}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}}}}