AskAgento API
Information
Askagento API
    Bring-your-own-key (BYOK) LLM credentialspostAI ChatbotpostCORS for AI ChatbotoptionsAuto FilterpostCORS for Auto FilteroptionsInstallation statusgetInstall pluginpostInstall verifypostCORS preflightoptionsAuto LabelpostCORS for Auto LabeloptionsAI Agents & MCPpostCORS for AI AgentsoptionsCurrent subscription plangetAI Recommend (cross-sell)getAI Recommend (upsell)getAI SearchpostCORS for AI SearchoptionsUpdate product datapostUninstall pluginpostUsage limitsget
Schemas
powered by Zudoku
Welcome to AskAgento API
Welcome to AskAgento API

Askagento API

Install, uninstall, status, recommendations, search, chatbot, BYOK, label, filter, MCP, plan, usage.


Bring-your-own-key (BYOK) LLM credentials

POST
https://api.askagento.com/v1
/byok

Store or clear a merchant-supplied OpenAI or OpenRouter API key on the install record.

When a BYOK key is stored, POST /chatbot uses that key for inference and does not debit limits.tokens (the merchant pays their provider directly). Clearing removes the key and restores the shared AskAgento LLM path with normal token metering.

Providers: openai, openrouter only (OpenAI-compatible chat completions).

Authentication: Send X-Askagento-Site-Id: <site_id> and X-Askagento-Api-Key: <api_key> headers. <api_key> must be the secret key; the public key is rejected with 401.

Bring-your-own-key (BYOK) LLM credentials › Request Body

ByokRequest
action
​string · enum · required

set stores the merchant key; clear removes BYOK credentials from the install record.

Enum values:
set
clear
provider
​string · enum

Required when action=set.

Enum values:
openai
openrouter
api_key
​string

Merchant LLM API key. Required when action=set. Never logged by the API.

model
​string

Optional model id for action=set (e.g. gpt-5-mini for OpenAI, or an OpenRouter model id). When omitted, the chatbot uses the server default (OpenRouter ids are prefixed with openai/ when needed).

Bring-your-own-key (BYOK) LLM credentials › Responses

BYOK config stored or cleared

ByokResponse
status
​string · required
site_id
​string · required
byok
​boolean · required

True when a BYOK key is stored after this request; false after clear.

provider
​string · enum

Present when byok is true (the provider just stored).

Enum values:
openai
openrouter
POST/byok
curl https://api.askagento.com/v1/byok \ --request POST \ --header 'Content-Type: application/json' \ --header 'X-Askagento-Site-Id: <api-key>' \ --header 'X-Askagento-Api-Key: <api-key>' \ --data '{ "action": "set", "provider": "openai", "api_key": "api_key", "model": "model" }'
Example Request Body
{ "action": "set", "provider": "openai", "api_key": "api_key", "model": "model" }
json
Example Responses
{ "status": "ok", "site_id": "site_id", "byok": true, "provider": "openai" }
json
application/json

AI Chatbot

POST
https://api.askagento.com/v1
/chatbot

Sends a conversation to a configured chat model.

action=chat — The last user message drives semantic product search against the site's catalogue (up to 12 matches). Matching products are injected as a system message before the LLM request. Retrieval does not debit limits.searches. If search or catalogue load fails, the chat continues without product context.

action=health — Minimal connectivity check: messages is ignored, completion is capped at 3 tokens, and products_retrieved is always 0. Upstream usage.total_tokens is still debited from limits.tokens when that limit is tracked (typically a few tokens), unless BYOK is active (see below).

BYOK — If the site has a merchant key stored via POST /byok, that key is used instead of the shared AskAgento LLM credentials. Token preflight and limits.tokens debit are skipped while BYOK is active (usage.billed_tokens is 0).

Token preflight (429 when limits.tokens is present and <= 0) applies when BYOK is not active.

Authentication: Send X-Askagento-Site-Id: <site_id> and X-Askagento-Api-Key: <api_key> headers. <api_key> can be the public key or the secret key; use the public key in browser code and AI agent configs.

AI Chatbot › Request Body

ChatbotRequest
action
​string · enum

chat — full conversation; last user turn drives product retrieval (see POST /chatbot). health — connectivity probe; messages optional and ignored; max_completion_tokens ignored.

Enum values:
chat
health
Default: chat
​ChatMessage[] · maxItems: 24

Required when action=chat (non-empty after normalization); omitted or ignored for health. Up to 24 turns; each content truncated to 12 000 chars.

max_completion_tokens
​integer · max: 4096

Alias max_tokens also accepted; capped at 4096. Ignored when action=health (server uses 3).

Default: 1024

AI Chatbot › Responses

Chat reply with usage and limit information

ChatbotResponse
site_id
​string · required
action
​string · enum · required
Enum values:
chat
health
latency_ms
​integer · required

Round-trip latency to the chat provider in milliseconds

​object · required
reply
​string · required

Text reply from the model

products_retrieved
​integer · required

Number of catalogue products injected as context for action=chat; always 0 for health

limits_tokens_remaining
​integer | null

Remaining token quota for the site after this call; null if no quota is set

POST/chatbot
curl https://api.askagento.com/v1/chatbot \ --request POST \ --header 'Content-Type: application/json' \ --header 'X-Askagento-Site-Id: <api-key>' \ --header 'X-Askagento-Api-Key: <api-key>' \ --data '{ "action": "chat", "messages": [ { "role": "system", "content": "content" } ], "max_completion_tokens": 1024 }'
Example Request Body
{ "action": "chat", "messages": [ { "role": "system", "content": "content" } ], "max_completion_tokens": 1024 }
json
Example Responses
{ "site_id": "site_id", "action": "chat", "latency_ms": 0, "usage": { "total_tokens": 0 }, "reply": "reply", "products_retrieved": 0, "limits_tokens_remaining": 0 }
json
application/json

CORS for AI Chatbot

OPTIONS
https://api.askagento.com/v1
/chatbot

No request body. Response includes CORS headers (Access-Control-Allow-Origin, Access-Control-Allow-Headers including X-Askagento-Site-Id, X-Askagento-Api-Key, Content-Type) so browsers may POST /chatbot.

CORS for AI Chatbot › Responses

200

Empty JSON body

OPTIONS/chatbot
curl https://api.askagento.com/v1/chatbot \ --request OPTIONS
Example Responses
{}
json
application/json

Auto Filter

POST
https://api.askagento.com/v1
/filter

Auto Filter pipeline (no LLM). analyze lists attribute names found in the synced catalog; generate echoes the merchant-selected canonical_filters; upload stores the selection on the catalog snapshot. Accepts action or filter_action (analyze, generate, upload, export). Optional canonical_filters is an alias for canonical_attributes.

Authentication: Send X-Askagento-Site-Id: <site_id> and X-Askagento-Api-Key: <api_key> headers. <api_key> must be the secret key; the public key is rejected with 401.

Auto Filter › Request Body

FilterRequest
action
​string · enum
Enum values:
analyze
generate
upload
export
filter_action
​string · enum

Alias for action; supply either action or filter_action.

Enum values:
analyze
generate
upload
export
canonical_filters
​string[]

Alias for canonical_attributes when generating attribute filters.

Auto Filter › Responses

Filter action result (analyze / generate / upload / export).

Shape depends on `mode` and `action`. `generated_preview`, `uploaded_products` (upload), `filename` (export), and informational `message`.
LabelFilterJsonResponse
site_id
​string
mode
​string
action
​string
Additional properties are allowed
POST/filter
curl https://api.askagento.com/v1/filter \ --request POST \ --header 'Content-Type: application/json' \ --header 'X-Askagento-Site-Id: <api-key>' \ --header 'X-Askagento-Api-Key: <api-key>' \ --data '{ "action": "analyze", "filter_action": "analyze", "canonical_filters": [ "string" ] }'
Example Request Body
{ "action": "analyze", "filter_action": "analyze", "canonical_filters": [ "string" ] }
json
Example Responses
{ "site_id": "site_id", "mode": "mode", "action": "action" }
json
application/json

CORS for Auto Filter

OPTIONS
https://api.askagento.com/v1
/filter

CORS for Auto Filter › Responses

200

Empty JSON body

OPTIONS/filter
curl https://api.askagento.com/v1/filter \ --request OPTIONS
Example Responses
{}
json
application/json

Installation status

GET
https://api.askagento.com/v1
/install

Retrieve installation metadata.

Authentication: Send X-Askagento-Site-Id: <site_id> and X-Askagento-Api-Key: <api_key> headers. <api_key> must be the secret key; the public key is rejected with 401.

Installation status › Responses

Install status response

InstallStatusResponse
site_id
​string
installed_at
​string | null · date-time
status_message
​string
status
​string
GET/install
curl https://api.askagento.com/v1/install \ --header 'X-Askagento-Site-Id: <api-key>' \ --header 'X-Askagento-Api-Key: <api-key>'
Example Responses
{ "site_id": "site_id", "installed_at": "2024-08-25T15:00:00Z", "status_message": "status_message", "status": "ok" }
json
application/json

Install plugin

POST
https://api.askagento.com/v1
/install

Install the plugin.

Install plugin › Request Body

InstallRequest
domain
​string · required
​Product[] · required
system
​string · enum · required

woocommerce — full catalogue with image + text data. knowledge_base — text-only Confluence/article chunks for askagento.com chat.

Enum values:
woocommerce
knowledge_base
plugin_version
​string
woocommerce_version
​string
total_products
​integer
shop_ip
​string

Optional IPv4 string for the shop host (plugin may send DNS resolution result).

Install plugin › Responses

Installation accepted for async processing

InstallAcceptedResponse
status
​string · required
site_id
​string · required

New site identifier; send it in X-Askagento-Site-Id on every authenticated call.

api_key
​string · required

Secret key; accepted on every authenticated route. Keep it on your server and never expose it in a web page.

public_key
​string · required

Public key; accepted only on POST /chatbot, POST /search and POST /mcp. Safe to embed in storefront pages and AI agent configs.

Example: pk_3fQx8ZkP2mLr7TnV1cWy9HsB
message
​string · required
POST/install
curl https://api.askagento.com/v1/install \ --request POST \ --header 'Content-Type: application/json' \ --data '{ "domain": "domain", "plugin_version": "plugin_version", "woocommerce_version": "woocommerce_version", "products": [ { "id": 0, "title": "title", "name": "name", "description": "description", "short_description": "short_description", "sku": "sku", "price": "price", "regular_price": "regular_price", "sale_price": "sale_price", "price_html": "price_html", "stock_quantity": 0, "status": "status", "featured": true, "on_sale": true, "permalink": "https://www.example.com/path/to/resource", "image_url": "https://www.example.com/path/to/resource", "categories": [ { "id": 0, "name": "name", "slug": "slug" } ], "tags": [ { "id": 0, "name": "name", "slug": "slug" } ], "attributes": [ {} ], "variations": [ {} ], "date_created": "2024-08-25T15:00:00Z", "date_modified": "2024-08-25T15:00:00Z", "created_at": "2024-08-25T15:00:00Z", "updated_at": "2024-08-25T15:00:00Z" } ], "total_products": 0, "shop_ip": "shop_ip", "system": "woocommerce" }'
Example Request Body
{ "domain": "domain", "plugin_version": "plugin_version", "woocommerce_version": "woocommerce_version", "products": [ { "id": 0, "title": "title", "name": "name", "description": "description", "short_description": "short_description", "sku": "sku", "price": "price", "regular_price": "regular_price", "sale_price": "sale_price", "price_html": "price_html", "stock_quantity": 0, "status": "status", "featured": true, "on_sale": true, "permalink": "https://www.example.com/path/to/resource", "image_url": "https://www.example.com/path/to/resource", "categories": [ { "id": 0, "name": "name", "slug": "slug" } ], "tags": [ { "id": 0, "name": "name", "slug": "slug" } ], "attributes": [ {} ], "variations": [ {} ], "date_created": "2024-08-25T15:00:00Z", "date_modified": "2024-08-25T15:00:00Z", "created_at": "2024-08-25T15:00:00Z", "updated_at": "2024-08-25T15:00:00Z" } ], "total_products": 0, "shop_ip": "shop_ip", "system": "woocommerce" }
json
Example Responses
{ "status": "accepted", "site_id": "site_id", "api_key": "api_key", "public_key": "pk_3fQx8ZkP2mLr7TnV1cWy9HsB", "message": "message" }
json
application/json

Install verify

POST
https://api.askagento.com/v1
/install/verify

Check that a shop can be reached from our servers before sending its catalogue to POST /install.

Installation reads product pages and images directly from the shop, so a shop that is local, resolves to a private address, or refuses image requests cannot be installed. Calling this first turns that into an immediate, explainable answer instead of a failure part-way through installation.

Send the shop domain and the URL of one product image. The check is a name check, a DNS lookup, and a single image fetch, so it returns in about a second.

verdict is one of:

  • pass — proceed with POST /install.
  • blocked — the install cannot succeed as configured; reason says why.
  • inconclusive — the shop could not be judged (timeout, rate limit). Offer a retry rather than treating it as a failure.

A blocked verdict is a normal, successful response: the check ran and the answer is no. Only malformed requests return 4xx.

codeverdictMeaning
reachablepassThe shop and its product images can be read.
local_domainblockedA local development address (localhost, .local, .test).
private_ipblockedThe domain resolves to a private address.
dns_unresolvedblockedThe domain does not resolve on the public internet.
tls_invalidblockedThe shop's certificate could not be verified.
password_protectedblockedThe shop asks our servers for a password.
image_forbiddenblockedImage requests are refused (hotlink protection or a firewall).
no_product_imagesblockedNo product has an image; products are indexed by their images.
connection_refusedblockedThe shop refused the connection.
tls_errorblockedThe TLS handshake with the shop failed.
unsupported_schemeblockedThe image URL is not http or https.
non_standard_portblockedThe image URL uses a port other than 80 or 443.
invalid_domainblockedNo usable shop domain was supplied.
image_not_foundinconclusiveThe sampled image 404s, but the shop answered.
image_not_an_imageinconclusiveThe image URL returned a page, not an image file.
rate_limitedinconclusiveThe shop rate-limited the request.
timeoutinconclusiveThe shop did not answer in time.
network_errorinconclusiveThe shop could not be contacted.
shop_errorinconclusiveThe shop returned a 5xx for the sampled image.
unexpected_statusinconclusiveThe image returned an unexpected status.
bad_redirectinconclusiveThe shop redirected without a destination.
too_many_redirectsinconclusiveThe image URL redirected too many times.

Treat unknown codes by their verdict — codes may be added.

No API key: this runs before POST /install issues one.

Install verify › Request Body

InstallVerifyRequest
domain
​string · required

Shop host name, e.g. shop.example.com. A full URL is also accepted.

Example: shop.example.com
image_url
​string

URL of one product image, picked at random from the catalogue about to be installed. Products are indexed by their images, so a catalogue without one cannot be installed: omitting it yields blocked (no_product_images).

Example: https://shop.example.com/wp-content/uploads/2026/01/hat.jpg

Install verify › Responses

Reachability verdict (including blocked, which is a normal result)

InstallVerifyResponse
ok
​boolean

True only when verdict is pass.

verdict
​string · enum
Enum values:
pass
blocked
inconclusive
code
​string

Machine-readable outcome, e.g. reachable, local_domain, private_ip, dns_unresolved, tls_invalid, password_protected, image_forbidden, image_not_found, no_product_images, rate_limited, timeout.

Example: image_forbidden
reason
​string

Sentence suitable for display to the shop administrator.

Example: The shop refuses image requests from our servers (hotlink protection or a firewall).
​object[]

Per-check detail, in the order the checks ran.

POST/install/verify
curl https://api.askagento.com/v1/install/verify \ --request POST \ --header 'Content-Type: application/json' \ --data '{ "domain": "shop.example.com", "image_url": "https://shop.example.com/wp-content/uploads/2026/01/hat.jpg" }'
Example Request Body
{ "domain": "shop.example.com", "image_url": "https://shop.example.com/wp-content/uploads/2026/01/hat.jpg" }
json
Example Responses
{ "ok": true, "verdict": "pass", "code": "reachable", "reason": "Your shop is publicly reachable.", "checks": [ { "id": "domain", "verdict": "pass", "code": "domain_ok", "reason": "The shop domain is a public name." }, { "id": "dns", "verdict": "pass", "code": "dns_ok", "reason": "shop.example.com resolves to the public address 203.0.113.10." }, { "id": "image", "verdict": "pass", "code": "image_ok", "reason": "Product images are reachable from our servers." } ] }
json
application/json

CORS preflight

OPTIONS
https://api.askagento.com/v1
/install/verify

CORS preflight › Responses

200

Preflight headers

No data returned
OPTIONS/install/verify
curl https://api.askagento.com/v1/install/verify \ --request OPTIONS
Example Responses
No example specified for this content type

Auto Label

POST
https://api.askagento.com/v1
/label

Loads the site's product JSON, then runs analyze (suggest canonical names), generate (LLM proposals stored on products and catalogue), upload (persist generated labels into the catalogue in object storage), or export (download-ready payload). Debiting token quota uses the same mechanism as chat/search.

Modes: attributes, categories, tags. Actions: analyze, generate, upload, export.

Authentication: Send X-Askagento-Site-Id: <site_id> and X-Askagento-Api-Key: <api_key> headers. <api_key> must be the secret key; the public key is rejected with 401.

Auto Label › Request Body

LabelRequest
mode
​string · enum · required
Enum values:
attributes
categories
tags
action
​string · enum · required
Enum values:
analyze
generate
upload
export
canonical_attributes
​string[]
canonical_categories
​string[]
canonical_tags
​string[]

Auto Label › Responses

Success shape varies by mode and action (counts, previews, keys, catalogue upload status).

Shape depends on `mode` and `action`. `generated_preview`, `uploaded_products` (upload), `filename` (export), and informational `message`.
LabelFilterJsonResponse
site_id
​string
mode
​string
action
​string
Additional properties are allowed
POST/label
curl https://api.askagento.com/v1/label \ --request POST \ --header 'Content-Type: application/json' \ --header 'X-Askagento-Site-Id: <api-key>' \ --header 'X-Askagento-Api-Key: <api-key>' \ --data '{ "mode": "attributes", "action": "analyze", "canonical_attributes": [ "string" ], "canonical_categories": [ "string" ], "canonical_tags": [ "string" ] }'
Example Request Body
{ "mode": "attributes", "action": "analyze", "canonical_attributes": [ "string" ], "canonical_categories": [ "string" ], "canonical_tags": [ "string" ] }
json
Example Responses
{ "site_id": "site_id", "mode": "mode", "action": "action" }
json
application/json

CORS for Auto Label

OPTIONS
https://api.askagento.com/v1
/label

CORS for Auto Label › Responses

200

Empty JSON body

OPTIONS/label
curl https://api.askagento.com/v1/label \ --request OPTIONS
Example Responses
{}
json
application/json

AI Agents & MCP

POST
https://api.askagento.com/v1
/mcp

MCP 2024-11-05 over HTTP. Every request is a JSON-RPC 2.0 POST.

Supported methods:

  • initialize — server capabilities and protocol version.
  • notifications/initialized — acknowledged silently (empty 200 body).
  • tools/call — execute a tool (see tool list below).
  • tools/list — catalogue of available tools.

tools/call tools (alphabetical):

  • chat_with_shop — conversational shop assistant (message, optional history); delegates to POST /chatbot with action=chat (product retrieval + LLM). Debits limits.tokens like /chatbot.
  • get_catalogue_stats — orientation summary: total and published product count, price range, number of distinct categories and tags, featured and on-sale counts (no arguments). Reads the stored S3 catalogue; no quota debit.
  • get_featured_products — curated product list: list_type one of featured (merchant-starred), on_sale (active discounts), or new_arrivals (sorted by date_created descending); limit 1–50 (default 12). Reads the stored S3 catalogue; no quota debit.
  • get_product_by_id — full detail for one product by numeric product_id: title, URL, image, price, categories, tags, description (up to 400 chars). Reads the stored S3 catalogue; no quota debit.
  • get_shop_status — install status, plan, and remaining usage quotas (no arguments).
  • get_similar_products — cross-sell and/or upsell neighbors for one product_id (optional recommendation_type, limit). Reads the same precomputed similarity bundle as /recommend/* (install-time catalogue similarity index, no LLM); no quota debit.
  • list_categories — all product categories in the catalogue with name, slug, and product count. No quota debit.
  • list_tags — all product tags in the catalogue with name, slug, and product count. No quota debit.
  • search_products — semantic search by text, image, or both (text and/or image_base64, optional modality, limit); debits limits.searches when tracked.

Successful tool calls and protocol errors (initialize, unknown method, etc.) return HTTP 200 with a JSON-RPC 2.0 body. Auth and site lookup failures also use HTTP 200 with JSON-RPC error objects (codes -32001 unauthorized, -32004 site not found) so MCP clients can always parse the envelope. HTTP 400 is reserved for a non-JSON or non-JSON-RPC request body at the transport layer.

Authentication: Send X-Askagento-Site-Id: <site_id> and X-Askagento-Api-Key: <api_key> headers. <api_key> can be the public key or the secret key; use the public key in browser code and AI agent configs.

AI Agents & MCP › Request Body

McpRequest
jsonrpc
​string · enum · required
Enum values:
2.0
method
​string · required

One of: initialize, notifications/initialized, tools/call, tools/list

​

Request id (omit for notifications)

​object

For tools/call: {"name": "chat_with_shop"|"get_catalogue_stats"|"get_featured_products"|"get_product_by_id"|"get_shop_status"|"get_similar_products"|"list_categories"|"list_tags"|"search_products", "arguments": {...}}

AI Agents & MCP › Responses

JSON-RPC 2.0 response (result or error)

McpResponse
jsonrpc
​string · enum
Enum values:
2.0
​
​object | null
error
​object | null
POST/mcp
curl https://api.askagento.com/v1/mcp \ --request POST \ --header 'Content-Type: application/json' \ --header 'X-Askagento-Site-Id: <api-key>' \ --header 'X-Askagento-Api-Key: <api-key>' \ --data '{ "jsonrpc": "2.0", "id": "string", "method": "method", "params": {} }'
Example Request Body
{ "jsonrpc": "2.0", "id": "string", "method": "method", "params": {} }
json
Example Responses
{ "jsonrpc": "2.0", "id": "string", "result": {}, "error": { "code": 0, "message": "message" } }
json
application/json

CORS for AI Agents

OPTIONS
https://api.askagento.com/v1
/mcp

CORS for AI Agents › Responses

200

Empty JSON body

OPTIONS/mcp
curl https://api.askagento.com/v1/mcp \ --request OPTIONS
Example Responses
{}
json
application/json

Current subscription plan

GET
https://api.askagento.com/v1
/plan

Returns the current plan slug and display label for the site. Every API capability is available on every plan; the plan sets catalogue capacity and included monthly usage only.

Authentication: Send X-Askagento-Site-Id: <site_id> and X-Askagento-Api-Key: <api_key> headers. <api_key> must be the secret key; the public key is rejected with 401.

Current subscription plan › Responses

Plan response

PlanResponse
site_id
​string
plan
​string | null

Plan slug (free, basic, pro); null if no plan is set

plan_label
​string | null

Human-readable plan label

GET/plan
curl https://api.askagento.com/v1/plan \ --header 'X-Askagento-Site-Id: <api-key>' \ --header 'X-Askagento-Api-Key: <api-key>'
Example Responses
{ "site_id": "site_id", "plan": "plan", "plan_label": "plan_label" }
json
application/json

AI Recommend (cross-sell)

GET
https://api.askagento.com/v1
/recommend/cross-sell

Precomputed cross-sell recommendations for the registered catalogue (stored in object storage). Built during installation from install-time catalogue similarity indexes (no LLM).

Authentication: Send X-Askagento-Site-Id: <site_id> and X-Askagento-Api-Key: <api_key> headers. <api_key> must be the secret key; the public key is rejected with 401.

AI Recommend (cross-sell) › Responses

Recommendations JSON from object storage

RecommendationsPayload
site_id
​string
generated_at
​string

ISO 8601 timestamp (UTC) with Z suffix

​object

Map of source product id to cross-sell targets (similarity-ranked)

​object

Map of source product id (string) to ranked neighbor list

GET/recommend/cross-sell
curl https://api.askagento.com/v1/recommend/cross-sell \ --header 'X-Askagento-Site-Id: <api-key>' \ --header 'X-Askagento-Api-Key: <api-key>'
Example Responses
{ "site_id": "site_id", "generated_at": "generated_at", "cross_sells": { "key": [ { "product_id": "product_id", "distance": 0, "title": "title", "image_url": "image_url", "source": "source" } ] }, "recommendations": { "key": [ { "product_id": "product_id", "distance": 0, "title": "title", "image_url": "image_url", "source": "source" } ] } }
json
application/json

AI Recommend (upsell)

GET
https://api.askagento.com/v1
/recommend/upsell

Precomputed upsell recommendations for the registered catalogue (stored in object storage). Built during installation from install-time catalogue similarity indexes (no LLM).

Authentication: Send X-Askagento-Site-Id: <site_id> and X-Askagento-Api-Key: <api_key> headers. <api_key> must be the secret key; the public key is rejected with 401.

AI Recommend (upsell) › Responses

Recommendations JSON from object storage

RecommendationsPayload
site_id
​string
generated_at
​string

ISO 8601 timestamp (UTC) with Z suffix

​object

Map of source product id to cross-sell targets (similarity-ranked)

​object

Map of source product id (string) to ranked neighbor list

GET/recommend/upsell
curl https://api.askagento.com/v1/recommend/upsell \ --header 'X-Askagento-Site-Id: <api-key>' \ --header 'X-Askagento-Api-Key: <api-key>'
Example Responses
{ "site_id": "site_id", "generated_at": "generated_at", "cross_sells": { "key": [ { "product_id": "product_id", "distance": 0, "title": "title", "image_url": "image_url", "source": "source" } ] }, "recommendations": { "key": [ { "product_id": "product_id", "distance": 0, "title": "title", "image_url": "image_url", "source": "source" } ] } }
json
application/json

AI Search

POST
https://api.askagento.com/v1
/search

Search endpoint for text and image search.

Omit modality to infer from the body: text only → text, image_base64 only → image, both present → both. Setting both requires text (≥2 chars) and image_base64. Prefer setting modality explicitly for MCP contracts so the search mode is declared rather than inferred.

Each successful search debits one from limits.searches when that limit is tracked.

Authentication: Send X-Askagento-Site-Id: <site_id> and X-Askagento-Api-Key: <api_key> headers. <api_key> can be the public key or the secret key; use the public key in browser code and AI agent configs.

AI Search › Request Body

SearchRequest
text
​string

Search text, at least 2 characters

image_base64
​string

Base64-encoded image bytes. A leading data:image/...;base64, prefix is stripped if present. Never fetched over the network.

modality
​string · enum

Omit to infer from the body: text only → text, image_base64 only → image, both present → both. Setting both requires text (≥2 chars) and image_base64.

Enum values:
text
image
both
limit
​integer · min: 1 · max: 50
Default: 12

AI Search › Responses

Ranked product hits

SearchResponse
site_id
​string · required
modality
​string · enum · required
Enum values:
text
image
both
​SearchHit[] · required
query
​string

Echoed text query when modality is text or both

POST/search
curl https://api.askagento.com/v1/search \ --request POST \ --header 'Content-Type: application/json' \ --header 'X-Askagento-Site-Id: <api-key>' \ --header 'X-Askagento-Api-Key: <api-key>' \ --data '{ "text": "text", "image_base64": "image_base64", "modality": "text", "limit": 12 }'
Example Request Body
{ "text": "text", "image_base64": "image_base64", "modality": "text", "limit": 12 }
json
Example Responses
{ "site_id": "site_id", "modality": "text", "query": "query", "results": [ { "product_id": "product_id", "title": "title", "image_url": "image_url", "distance": 0 } ] }
json
application/json

CORS for AI Search

OPTIONS
https://api.askagento.com/v1
/search

No request body. Response includes CORS headers (Access-Control-Allow-Origin, Access-Control-Allow-Headers including X-Askagento-Site-Id, X-Askagento-Api-Key, Content-Type) so browsers may POST /search.

CORS for AI Search › Responses

200

Empty JSON body

OPTIONS/search
curl https://api.askagento.com/v1/search \ --request OPTIONS
Example Responses
{}
json
application/json

Update product data

POST
https://api.askagento.com/v1
/update

Push the shop's current product catalogue for an installed site (scheduled or manual sync). Stores product JSON in object storage and updates the install record's product-data hash.

Authentication: Send X-Askagento-Site-Id: <site_id> and X-Askagento-Api-Key: <api_key> headers. <api_key> must be the secret key; the public key is rejected with 401.

Update product data › Request Body

UpdateRequest
​Product[] · required
system
​string · enum · required
Enum values:
woocommerce
domain
​string
plugin_version
​string
woocommerce_version
​string
total_products
​integer

Update product data › Responses

Product data accepted

UpdateResponse
status
​string · required
site_id
​string · required
synced_products
​integer · required
update_needed
​boolean · required

True when the catalogue hash changed on this sync (re-embed required). Unchanged-hash syncs do not clear a previously true flag.

message
​string · required
POST/update
curl https://api.askagento.com/v1/update \ --request POST \ --header 'Content-Type: application/json' \ --header 'X-Askagento-Site-Id: <api-key>' \ --header 'X-Askagento-Api-Key: <api-key>' \ --data '{ "domain": "domain", "plugin_version": "plugin_version", "woocommerce_version": "woocommerce_version", "products": [ { "id": 0, "title": "title", "name": "name", "description": "description", "short_description": "short_description", "sku": "sku", "price": "price", "regular_price": "regular_price", "sale_price": "sale_price", "price_html": "price_html", "stock_quantity": 0, "status": "status", "featured": true, "on_sale": true, "permalink": "https://www.example.com/path/to/resource", "image_url": "https://www.example.com/path/to/resource", "categories": [ { "id": 0, "name": "name", "slug": "slug" } ], "tags": [ { "id": 0, "name": "name", "slug": "slug" } ], "attributes": [ {} ], "variations": [ {} ], "date_created": "2024-08-25T15:00:00Z", "date_modified": "2024-08-25T15:00:00Z", "created_at": "2024-08-25T15:00:00Z", "updated_at": "2024-08-25T15:00:00Z" } ], "total_products": 0, "system": "woocommerce" }'
Example Request Body
{ "domain": "domain", "plugin_version": "plugin_version", "woocommerce_version": "woocommerce_version", "products": [ { "id": 0, "title": "title", "name": "name", "description": "description", "short_description": "short_description", "sku": "sku", "price": "price", "regular_price": "regular_price", "sale_price": "sale_price", "price_html": "price_html", "stock_quantity": 0, "status": "status", "featured": true, "on_sale": true, "permalink": "https://www.example.com/path/to/resource", "image_url": "https://www.example.com/path/to/resource", "categories": [ { "id": 0, "name": "name", "slug": "slug" } ], "tags": [ { "id": 0, "name": "name", "slug": "slug" } ], "attributes": [ {} ], "variations": [ {} ], "date_created": "2024-08-25T15:00:00Z", "date_modified": "2024-08-25T15:00:00Z", "created_at": "2024-08-25T15:00:00Z", "updated_at": "2024-08-25T15:00:00Z" } ], "total_products": 0, "system": "woocommerce" }
json
Example Responses
{ "status": "ok", "site_id": "site_id", "synced_products": 0, "update_needed": true, "message": "message" }
json
application/json

Uninstall plugin

POST
https://api.askagento.com/v1
/uninstall

Uninstall the plugin and remove all indexed data for the site.

Authentication: Send X-Askagento-Site-Id: <site_id> and X-Askagento-Api-Key: <api_key> headers. <api_key> must be the secret key; the public key is rejected with 401.

Uninstall plugin › Request Body

UninstallRequest
system
​string · enum · required
Enum values:
woocommerce
knowledge_base
domain
​string
plugin_version
​string
woocommerce_version
​string

Uninstall plugin › Responses

Uninstall completed

StatusOkResponse
status
​string
POST/uninstall
curl https://api.askagento.com/v1/uninstall \ --request POST \ --header 'Content-Type: application/json' \ --header 'X-Askagento-Site-Id: <api-key>' \ --header 'X-Askagento-Api-Key: <api-key>' \ --data '{ "system": "woocommerce", "domain": "domain", "plugin_version": "plugin_version", "woocommerce_version": "woocommerce_version" }'
Example Request Body
{ "system": "woocommerce", "domain": "domain", "plugin_version": "plugin_version", "woocommerce_version": "woocommerce_version" }
json
Example Responses
{ "status": "ok" }
json
application/json

Usage limits

GET
https://api.askagento.com/v1
/usage

Returns the current plan, remaining per-site limits (tokens, searches), the tier-level maximums, and the catalogue product count against the number of products the plan indexes. Every API capability is available on every plan; a plan sets only catalogue capacity and included monthly usage. When the catalogue is larger than the plan indexes (over_product_limit: true), catalogue-backed endpoints return 403 with code: product_limit_exceeded until the catalogue is covered by a larger plan or reduced in size.

Authentication: Send X-Askagento-Site-Id: <site_id> and X-Askagento-Api-Key: <api_key> headers. <api_key> must be the secret key; the public key is rejected with 401.

Usage limits › Responses

Usage response

UsageResponse
site_id
​string
plan
​string | null

Plan slug; null if no plan is set

plan_label
​string | null
​UsageLimits

Remaining monthly plan allowance for this site; null if no limits are tracked. Reset to the tier maximum each billing period. Does not include add-on packs.

​UsageLimits

Unspent one-time add-on pack credits, omitted keys meaning zero; null when the site has none. These do not expire and are only spent once limits reaches zero, so the site's true remaining balance is limits + pack_units.

​UsageLimits

Tier-level maximums for the current plan; null if no plan is set. Includes a products field (how many products the plan indexes) in addition to tokens/searches.

product_count
​integer | null

Number of products in the shop's catalogue; null if not yet recorded

max_products
​integer | null

Number of products the service indexes on the current plan; null if no plan is set.

over_product_limit
​boolean

True when the catalogue is larger than the current plan indexes. While true, catalogue-backed endpoints return 403 (code: product_limit_exceeded) until the catalogue is covered by a larger plan or reduced in size.

GET/usage
curl https://api.askagento.com/v1/usage \ --header 'X-Askagento-Site-Id: <api-key>' \ --header 'X-Askagento-Api-Key: <api-key>'
Example Responses
{ "site_id": "site_id", "plan": "plan", "plan_label": "plan_label", "limits": { "tokens": 0, "searches": 0 }, "pack_units": { "tokens": 0, "searches": 0 }, "plan_max_limits": { "tokens": 0, "searches": 0 }, "product_count": 0, "max_products": 0, "over_product_limit": true }
json
application/json