Constructor AI Shopping Agent API
Conversational product-discovery API returning intent-based suggestions over a Server-Sent Events stream, plus AI-generated item questions and answers.
Conversational product-discovery API returning intent-based suggestions over a Server-Sent Events stream, plus AI-generated item questions and answers.
openapi: 3.1.0
info:
title: AI Shopping Agent
summary: AI Shopping Agent
description: API documentation for the AI shopping and product insights agent.
version: v1
servers:
- url: https://agent.cnstrc.com
paths:
/v1/intent/{query}:
get:
tags:
- Results
summary: Retrieve by intent
description: Retrieves AI powered product discovery suggestions based on conversational free-form text. Returns results in small batches using a real time [Server-sent Events](https://developer.mozilla.org/en-US/docs/Web/API/Server-sent_events/Using_server-sent_events) stream for a dynamic user experience.
operationId: v1-asa-retrieve-intent
parameters:
- description: The query provided by the user as free-form text.
required: true
schema:
type: string
title: Intent
description: The query provided by the user as free-form text.
name: query
in: path
- description: The key of the index to use.
required: true
schema:
type: string
title: Key
description: The key of the index to use.
name: key
in: query
- description: A unique identifier for the conversation thread. This ID links multiple requests to the same conversation.
required: false
schema:
type: string
format: uuid
title: Thread ID
description: A unique identifier for the conversation thread. This ID links multiple requests to the same conversation.
name: thread_id
in: query
- description: A URL-encoded JSON string containing filters (inaccessible to end users) used to narrow the result set. Applied before filters accessible to end users. Does not affect facet counts. Only results that match the filters are returned. More details on https://docs.constructor.com/reference/shared-pre-filter-expressions
required: false
schema:
type: string
title: Pre Filter Expression
description: A URL-encoded JSON string containing filters (inaccessible to end users) used to narrow the result set. Applied before filters accessible to end users. Does not affect facet counts. Only results that match the filters are returned. More details on https://docs.constructor.com/reference/shared-pre-filter-expressions
name: pre_filter_expression
in: query
- description: The domain specifying a set of specific instructions for processing the intent, e.g., 'recipes', 'sportsgear'.
required: true
schema:
type: string
title: Domain
description: The domain specifying a set of specific instructions for processing the intent, e.g., 'recipes', 'sportsgear'.
name: domain
in: query
- description: Enable or disable the moderation check.
required: false
schema:
type: boolean
title: Guard
description: Enable or disable the moderation check.
default: false
name: guard
in: query
- description: The maximum number of result events to return.
required: false
schema:
type: integer
title: Num Result Events
description: The maximum number of result events to return.
name: num_result_events
in: query
- description: '**Deprecated. Please, use ``num_results_per_event`` instead.**'
required: false
schema:
type: integer
title: Num Results Per Page
description: '**Deprecated. Please, use ``num_results_per_event`` instead.**'
name: num_results_per_page
in: query
deprecated: true
- description: The maximum number of results to return per ``search_result`` event.
required: false
schema:
type: integer
title: Num Results Per Event
description: The maximum number of results to return per ``search_result`` event.
name: num_results_per_event
in: query
- description: An object containing options to format different aspects of the response.
required: false
schema:
title: Fmt Options
description: An object containing options to format different aspects of the response.
allOf:
- $ref: '#/components/schemas/FmtOptions'
style: deepObject
explode: true
name: fmt_options
in: query
- description: A URL-encoded JSON string. More details on https://docs.constructor.com/reference/search-search-results#using-the-qs-parameter
required: false
schema:
type: string
title: Qs
description: A URL-encoded JSON string. More details on https://docs.constructor.com/reference/search-search-results#using-the-qs-parameter
name: qs
in: query
- description: The id of the client and version that the request is coming from, such as `cio-js-2.90`.
required: false
schema:
type: string
title: C
description: The id of the client and version that the request is coming from, such as `cio-js-2.90`.
name: c
in: query
- description: A customer defined context (such as `vip-club-member`) used to evaluate redirect or refined tag rules. Pass multiple segments by passing multiple `us` arguments.
required: false
schema:
items:
type: string
type: array
title: us
description: A customer defined context (such as `vip-club-member`) used to evaluate redirect or refined tag rules. Pass multiple segments by passing multiple `us` arguments.
name: us
in: query
- description: A customer generated anonymized identifier for a user on a customer website. It should only be sent for logged in customers and helps constructor to tie multiple client and session ID's together to form a behavioral data profile across devices.
required: false
schema:
type: string
title: Ui
description: A customer generated anonymized identifier for a user on a customer website. It should only be sent for logged in customers and helps constructor to tie multiple client and session ID's together to form a behavioral data profile across devices.
name: ui
in: query
- description: An integer representing the users session number (starting with `1`), incremented after a 30 minute period of inactivity.
required: false
schema:
type: integer
title: S
description: An integer representing the users session number (starting with `1`), incremented after a 30 minute period of inactivity.
name: s
in: query
- description: A globally unique identifier for the user browser (or mobile application instance) making the request.
required: false
schema:
type: string
title: I
description: A globally unique identifier for the user browser (or mobile application instance) making the request.
name: i
in: query
responses:
'200':
description: SSE stream containing a series of events with discovered items or AI generated textual messages.
content:
text/event-stream:
schema:
anyOf:
- properties:
event:
type: string
default: start
data:
$ref: '#/components/schemas/Start'
type: object
required:
- event
- data
- properties:
event:
type: string
default: end
data:
$ref: '#/components/schemas/End'
type: object
required:
- event
- data
- properties:
event:
type: string
default: server_error
data:
$ref: '#/components/schemas/ServerError'
type: object
required:
- event
- data
- properties:
event:
type: string
default: message
data:
$ref: '#/components/schemas/Message'
type: object
required:
- event
- data
- properties:
event:
type: string
default: image_meta
data:
$ref: '#/components/schemas/ImageMeta'
type: object
required:
- event
- data
- properties:
event:
type: string
default: article_reference
data:
$ref: '#/components/schemas/ArticleReference'
type: object
required:
- event
- data
- properties:
event:
type: string
default: search_result
data:
$ref: '#/components/schemas/SSESearchResponse'
type: object
required:
- event
- data
- properties:
event:
type: string
default: follow_up_refinement
data:
$ref: '#/components/schemas/SSEFollowUpRefinement'
type: object
required:
- event
- data
- properties:
event:
type: string
default: recipe_info
data:
$ref: '#/components/schemas/RecipeInfo'
type: object
required:
- event
- data
- properties:
event:
type: string
default: recipe_instructions
data:
$ref: '#/components/schemas/RecipeInstructions'
type: object
required:
- event
- data
examples:
Message:
summary: Message
description: Represents a simple text message. Usually emitted prior to the one or multiple search_result events, giving textual explanation why are those results relevant to the shopper. Can contain a question for the shopper, asking for clarification or suggesting follow-up queries to further refine result set.
value: 'event: message
data: {''event'': ''message'', ''intent_result_id'': ''abcd1234-56ef-7890-ab12-1234567890ab'', ''text'': ''A collection of refreshing summer recipes.''}'
ImageMeta:
summary: ImageMeta
description: ''
value: 'event: image_meta
data: {''event'': ''image_meta'', ''intent_result_id'': ''def01234-56ab-7890-cd12-1234567890ef'', ''item_id'': ''item12345'', ''image_url'': ''https://example.com/images/item12345.jpg'', ''image_url_small'': ''https://example.com/images/item12345-small.jpg''}'
ArticleReference:
summary: ArticleReference
description: ''
value: 'event: article_reference
data: {''event'': ''article_reference'', ''intent_result_id'': ''987fbc77-34ae-11d1-a456-426655440000'', ''source'': ''https://example.com/article/how-to-cook-rice'', ''title'': ''How to Cook Rice Perfectly Every Time'', ''image_url'': ''https://example.com/images/cooked-rice.jpg'', ''abstract'': ''Discover the secrets to cooking fluffy, perfect rice every time with our simple guide.''}'
SSESearchResponse:
summary: SSESearchResponse
description: An Event to encapsulate a SABR result.
value: 'event: search_result
data: {''event'': ''search_result'', ''intent_result_id'': ''abc12345-6789-de01-2345-6789abcdef01'', ''result_id'': ''res12345-6789-de01-2345-6789abcdef01'', ''response'': {''search_request'': {''display_name'': ''Italian'', ''search_term'': ''best Italian recipes'', ''params'': {''cuisine'': ''Italian'', ''difficulty'': ''easy''}}, ''alternative_search_requests'': [{''display_name'': ''Vegetarian Italian'', ''search_term'': ''vegetarian Italian recipes'', ''params'': {''cuisine'': ''Italian'', ''difficulty'': ''easy'', ''diet'': ''vegetarian''}}, {''display_name'': ''Quick Italian'', ''search_term'': ''quick Italian recipes'', ''params'': {''cuisine'': ''Italian'', ''difficulty'': ''easy'', ''time'': ''<30min''}}], ''results'': [''...'']}}'
SSEFollowUpRefinement:
summary: SSEFollowUpRefinement
description: Suggested refinement options for the follow-up question asked by the agent. Each option is a short label the shopper can select to narrow their intent.
value: 'event: follow_up_refinement
data: {''event'': ''follow_up_refinement'', ''intent_result_id'': ''abcd1234-56ef-7890-ab12-1234567890ab'', ''question'': ''Do you have any color preference?'', ''options'': [''Blue'', ''Red'', ''Green'']}'
RecipeInfo:
summary: RecipeInfo
description: An event that represents recipes' auxiliary information like cooking times & serving sizes.
value: 'event: recipe_info
data: {''event'': ''recipe_info'', ''intent_result_id'': ''123e4567-e89b-12d3-a456-426614174000'', ''recipe_title'': ''Classic Tomato Spaghetti'', ''prep_time_minutes'': 10, ''cook_time_minutes'': 20, ''number_of_servings'': 4, ''ingredients'': [''400g spaghetti'', ''1 garlic clove'', ''400g tin of tomatoes'', ''Handful of basil leaves'']}'
RecipeInstructions:
summary: RecipeInstructions
description: Step-by-step preparation instructions.
value: 'event: recipe_instructions
data: {''event'': ''recipe_instructions'', ''intent_result_id'': ''123e4567-e89b-12d3-a456-426614174000'', ''steps'': [''Boil water in a large pot.'', ''Add spaghetti and cook for 8-10 minutes or until al dente; drain.'', ''In a large skillet, cook garlic in olive oil over medium heat until lightly golden.'', ''Stir in tomatoes, and cook until heated through.'', ''Mix spaghetti with the sauce, and serve with basil leaves on top.''], ''text'': ''Serve with grated Parmesan cheese if desired.''}'
'400':
description: Invalid request parameters.
'422':
description: Validation Error
content:
application/json:
schema:
$ref: '#/components/schemas/HTTPValidationError'
'500':
description: Internal server error.
security: []
/v1/item_questions:
get:
tags:
- Results
summary: Retrieve questions
description: Retrieves AI powered list of frequently asked questions for the given item.
operationId: v1-asa-retrieve-item-questions
parameters:
- name: key
in: query
required: true
schema:
type: string
title: key
description: The key of the index to use.
description: The key of the index to use.
- name: item_id
in: query
required: true
schema:
type: string
title: Item ID
description: The id of the item to return questions for.
description: The id of the item to return questions for.
- name: variation_id
in: query
required: false
schema:
anyOf:
- type: string
- type: 'null'
title: Item variation ID
description: The id of the variation of the item to return questions for.
description: The id of the variation of the item to return questions for.
- name: num_results
in: query
required: false
schema:
anyOf:
- type: integer
- type: 'null'
title: Number of results
description: The number of questions to return.
description: The number of questions to return.
- description: The id of the client and version that the request is coming from, such as `cio-js-2.90`.
required: false
schema:
type: string
title: C
description: The id of the client and version that the request is coming from, such as `cio-js-2.90`.
name: c
in: query
- description: A customer defined context (such as `vip-club-member`) used to evaluate redirect or refined tag rules. Pass multiple segments by passing multiple `us` arguments.
required: false
schema:
items:
type: string
type: array
title: us
description: A customer defined context (such as `vip-club-member`) used to evaluate redirect or refined tag rules. Pass multiple segments by passing multiple `us` arguments.
name: us
in: query
- description: A customer generated anonymized identifier for a user on a customer website. It should only be sent for logged in customers and helps constructor to tie multiple client and session ID's together to form a behavioral data profile across devices.
required: false
schema:
type: string
title: Ui
description: A customer generated anonymized identifier for a user on a customer website. It should only be sent for logged in customers and helps constructor to tie multiple client and session ID's together to form a behavioral data profile across devices.
name: ui
in: query
- description: An integer representing the users session number (starting with `1`), incremented after a 30 minute period of inactivity.
required: false
schema:
type: integer
title: S
description: An integer representing the users session number (starting with `1`), incremented after a 30 minute period of inactivity.
name: s
in: query
- description: A globally unique identifier for the user browser (or mobile application instance) making the request.
required: false
schema:
type: string
title: I
description: A globally unique identifier for the user browser (or mobile application instance) making the request.
name: i
in: query
responses:
'200':
description: AI powered list of frequently asked questions for the given item.
content:
application/json:
schema:
$ref: '#/components/schemas/pdp__schema__item_questions_api_model__AsaItemQuestionsResponse'
'400':
description: Invalid request parameters.
'422':
description: Validation Error
content:
application/json:
schema:
$ref: '#/components/schemas/HTTPValidationError'
'500':
description: Internal server error.
security: []
/v1/item_questions/{question}/answer:
get:
tags:
- Results
summary: Retrieves answers
description: Retrieves AI powered answers to questions for a given item. If the client accepts [server-sent events](https://developer.mozilla.org/en-US/docs/Web/API/Server-sent_events/Using_server-sent_events) (text/event-stream content) response will be streamed back, otherwise complete response JSON is returned.
operationId: v1-asa-retrieve-item-questions-answer
parameters:
- name: question
in: path
required: true
schema:
type: string
title: question
description: The question provided by the user as free-form text.
description: The question provided by the user as free-form text.
- name: key
in: query
required: true
schema:
type: string
title: key
description: The key of the index to use.
description: The key of the index to use.
- name: item_id
in: query
required: true
schema:
type: string
title: Item ID
description: The id of the item to return answer(s) for.
description: The id of the item to return answer(s) for.
- description: A unique identifier for the conversation thread. This ID links multiple requests to the same conversation.
required: false
schema:
type: string
format: uuid
title: Thread ID
description: A unique identifier for the conversation thread. This ID links multiple requests to the same conversation.
name: thread_id
in: query
- name: variation_id
in: query
required: false
schema:
type: string
title: Item variation ID
description: The id of the variation of the item to return answer(s) for.
description: The id of the variation of the item to return answer(s) for.
- name: guard
in: query
required: false
schema:
type: boolean
title: Guard
description: Enable or disable the moderation check.
default: false
description: Enable or disable the moderation check.
- name: num_results
in: query
required: false
schema:
type: integer
title: Number of results
description: The number of answers to return.
description: The number of answers to return.
- description: The id of the client and version that the request is coming from, such as `cio-js-2.90`.
required: false
schema:
type: string
title: C
description: The id of the client and version that the request is coming from, such as `cio-js-2.90`.
name: c
in: query
- description: A customer defined context (such as `vip-club-member`) used to evaluate redirect or refined tag rules. Pass multiple segments by passing multiple `us` arguments.
required: false
schema:
items:
type: string
type: array
title: us
description: A customer defined context (such as `vip-club-member`) used to evaluate redirect or refined tag rules. Pass multiple segments by passing multiple `us` arguments.
name: us
in: query
- description: A customer generated anonymized identifier for a user on a customer website. It should only be sent for logged in customers and helps constructor to tie multiple client and session ID's together to form a behavioral data profile across devices.
required: false
schema:
type: string
title: Ui
description: A customer generated anonymized identifier for a user on a customer website. It should only be sent for logged in customers and helps constructor to tie multiple client and session ID's together to form a behavioral data profile across devices.
name: ui
in: query
- description: An integer representing the users session number (starting with `1`), incremented after a 30 minute period of inactivity.
required: false
schema:
type: integer
title: S
description: An integer representing the users session number (starting with `1`), incremented after a 30 minute period of inactivity.
name: s
in: query
- description: A globally unique identifier for the user browser (or mobile application instance) making the request.
required: false
schema:
type: string
title: I
description: A globally unique identifier for the user browser (or mobile application instance) making the request.
name: i
in: query
responses:
'200':
description: AI powered answer to question for a given item.
content:
application/json:
schema:
$ref: '#/components/schemas/pdp__schema__item_questions_api_model__AsaItemQuestionsAnswerResponse'
text/event-stream:
schema:
anyOf:
- type: object
properties:
event:
type: string
default: start
data:
$ref: '#/components/schemas/pdp__schema__item_questions_api_model__Start'
required:
- event
- data
- type: object
properties:
event:
type: string
default: end
data:
$ref: '#/components/schemas/pdp__schema__item_questions_api_model__End'
required:
- event
- data
- type: object
properties:
event:
type: string
default: server_error
data:
$ref: '#/components/schemas/pdp__schema__item_questions_api_model__ServerError'
required:
- event
- data
- type: object
properties:
event:
type: string
default: message
data:
$ref: '#/components/schemas/pdp__schema__item_questions_api_model__Message'
required:
- event
- data
- type: object
properties:
event:
type: string
default: follow_up_questions
data:
$ref: '#/components/schemas/pdp__schema__item_questions_api_model__SSEFollowUpQuestions'
required:
- event
- data
- type: object
properties:
event:
type: string
default: item_results
data:
$ref: '#/components/schemas/pdp__schema__item_questions_api_model__SSEItemResults'
required:
- event
- data
examples:
Start:
summary: Start
description: Event always emitted on the beginning of the server-sent event stream.
value: 'event: start
data: {''event'': ''start'', ''qna_result_id'': ''string'', ''thread_id'': ''string''}'
Message:
summary: Message
description: Event containing textual answer to the shopper's question.
value: 'event: message
data: {''event'': ''message'', ''qna_result_id'': ''string'', ''thread_id'': ''string'', ''text'': ''string''}'
FollowUpQuestions:
summary: Follow-up questions
description: Event containing sequence of follow-up questions shopper might ask.
value: 'event: follow_up_questions
data: {''event'': ''follow_up_questions'', ''qna_result_id'': ''string'', ''thread_id'': ''string'', ''questions'': [{''value'': ''string''}]'
ItemResults:
summary: Alternatives or complementary items
description: Event containing sequence of alternative/complementary items.
value: 'event: item_results
data: {''event'': ''item_results'', ''qna_result_id'': ''string'', ''thread_id'': ''string'', ''request'': {}, ''response'': {''results'': [{''value'': ''string'', ''matched_terms'': [''string''], ''data'': {''id'': ''string'', ''url'': ''string'', ''image_url'': ''string'', ''variation_id'': ''string'', ''facets'': [{''name'': ''string'', ''values'': [0, ''string'']}], ''groups'': [{''group_id'': ''string'', ''display_name'': ''string'', ''path'': ''/great-grandparent/grandparent/parent/'', ''path_list'': [{''id'': ''string'', ''display_name'': ''string''}]}]}, ''variations'': [{''data'': {''id'': ''string'', ''url'': ''string'', ''image_url'': ''string'', ''variation_id'': ''string'', ''facets'': [{''name'': ''string'', ''values'': [0, ''string'']}], ''groups'': [{''group_id'': ''string'', ''display_name'': ''string'', ''path'': ''/great-grandparent/grandparent/parent/'', ''path_list'': [{''id'': ''string'', ''display_name'': ''string''}]}]}, ''value'': ''string''}], ''variations_map'': {}, ''additionalProp'': {}}]}}'
ServerError:
summary: Server error
description: Event indicating that the internal server error occurred while processing request.
value: 'event: server_error
data: {''status_code'': 500, ''message'': ''Internal Server Error''}'
Ping:
summary: Ping
description: Event sent periodically to the caller to keep connection alive and prevent timeouts.
value: 'event: ping
data: {''time'': ''2025-06-02T00:00:00+01:00''}'
End:
summary: End
description: Event always closing the stream of server-sent events.
value: 'event: end
data: {''event'': ''end'', ''qna_result_id'': ''string'', ''thread_id'': ''string''}'
'400':
description: Invalid request parameters.
'422':
description: Validation Error
content:
application/json:
schema:
$ref: '#/components/schemas/HTTPValidationError'
'500':
description: Internal server error.
security: []
components:
schemas:
ArticleReference:
properties:
event:
type: string
enum:
- article_reference
title: event type
default: article_reference
intent_result_id:
type: string
title: Intent Result ID
thread_id:
type: string
format: uuid
title: Thread ID
source:
type: string
maxLength: 2083
minLength: 1
format: uri
title: article_url
title:
type: string
title: title
image_url:
type: string
maxLength: 2083
minLength: 1
format: uri
title: image_url
abstract:
type: string
title: abstract
type: object
required:
- intent_result_id
- source
- title
title: ArticleReference
example:
event: article_reference
intent_result_id: 987fbc77-34ae-11d1-a456-426655440000
source: https://example.com/article/how-to-cook-rice
title: How to Cook Rice Perfectly Every Time
image_url: https://example.com/images/cooked-rice.jpg
abstract: Discover the secrets to cooking fluffy, perfect rice every time with our simple guide.
AsaRequest:
properties:
intent:
type: string
title: Intent
description: The query provided by the user as free-form text.
key:
type: string
title: Key
description: The key of the index to use.
domain:
type: string
title: Domain
description: The domain specifying a set of specific instructions for processing the intent, e.g., 'recipes', 'sportsgear'.
thread_id:
type: string
format: uuid
title: Thread ID
description:
# --- truncated at 32 KB (63 KB total) ---
# Full source: https://raw.githubusercontent.com/api-evangelist/constructorio/refs/heads/main/openapi/constructorio-ai-shopping-agent-openapi.yml