Walker Formulation Academy for developers API reference Error catalog OpenAPI
Sections

Product cards

Methods in this section: 6. All methods

MethodPathDescriptionScopesStatus
GET/cardsList cardscards:readAvailable
POST/cardsCreate a cardcards:writeAvailable
GET/cards/{code}Get a cardcards:readAvailable
PATCH/cards/{code}Update a cardcards:writeAvailable
DELETE/cards/{code}Delete a cardcards:writeAvailable
POST/conversations/{id}/cardsSend cards to a conversationconversations:writeAvailable PII
GET /cards Available

#List cards

The account product cards ordered by sort, then by creation. ai_enabled=true|false — only cards available (or not) to the AI seller.

Scopes
cards:read
Rate limit
read
Idempotency
not required
Successful response
200 A page of cards.

Parameters

FieldTypeDescription
limitinteger
optional
In: query. Page size, 1–100, default 50.
cursorstring
optional
In: query. The next_cursor value from the previous response. Valid for 24 hours; start over when filters change.
ai_enabledboolean
optional
In: query. Filter by availability to the AI seller.

Response body

FieldTypeDescription
dataarray<Card>
required
next_cursorstring
required, may be null
Cursor of the next page; null — the list is exhausted. Valid for 24 hours.

Examples

Request
curl -X GET 'https://wfacademy.org/api/public/v1/cards' \
  -H 'Authorization: Bearer '"$API_KEY"
Response 200
{
  "data": [
    {
      "id": "EXAMPLE_ID",
      "code": "string",
      "name": "string",
      "description": null,
      "image_url": null,
      "price_text": null,
      "badge": null,
      "page_url": null,
      "buttons": [
        null
      ],
      "ai_enabled": false,
      "sort": 0,
      "active": false,
      "created_at": "2026-10-11T09:00:00Z",
      "updated_at": "2026-10-11T09:00:00Z"
    }
  ],
  "next_cursor": "EXAMPLE_CURSOR"
}
Error example
{
  "type": "https://wfacademy.org/developers/errors#scope_missing",
  "title": "Scope is missing",
  "status": 403,
  "code": "scope_missing",
  "detail": "EXAMPLE",
  "request_id": "req_EXAMPLE"
}

Examples are illustrative: the key in them is a placeholder (EXAMPLE), field values are made up.

Possible errors

invalid_api_key wrong_cell integration_inactive tenant_inactive ip_not_allowed feature_not_in_plan rate_limited wallet_suspended service_unavailable internal_error scope_missing validation_failed

POST /cards Available

#Create a card

Creates a product with a card. A taken code — validation_failed on /code. URLs: https:// or a path on your site ("/…") only; javascript:, data:, http: and another account storage path are rejected (validation_failed).

Scopes
cards:write
Rate limit
write
Idempotency
Idempotency-Key is required
Successful response
201 The card.

Parameters

FieldTypeDescription
Idempotency-Keystring
required
In: header. A unique string (usually a UUID v4), new for every new operation. A retry with the same key and body yields the same result.

Request body The card.

FieldTypeDescription
codestring
required
The card code, unique in the account: lowercase latin letters, digits, "_" and "-", up to 40 characters. The AI seller puts the [CARD:code] marker into its reply.
namestring
required
Name. Up to 120 characters.
descriptionstring
optional, may be null
Description. Up to 500 characters.
image_urlstring
optional, may be null
Image: https:// or the path of a file uploaded to your account storage.
page_urlstring
optional, may be null
Product page. Only https:// or a path on your site starting with "/" (resolved against the account primary domain).
badgestring
optional, may be null
Badge ("Bestseller"). Up to 30 characters.
price_textstring
optional, may be null
Price as text. Up to 40 characters.
buttonsarray<CardButton>
optional
Up to 3 buttons. Empty — a single "Learn more" button to page_url.
ai_enabledboolean
optional
The card is available to the AI seller: code, name and price go into its catalogue. Requires a code.
sortinteger
optional
Order in the AI seller catalogue and the operator picker (ascending).
activeboolean
optional
The product is active; an inactive card cannot be sent.

Response body

FieldTypeDescription
idstring
required
The product id.
codestring
required
The card code, unique in the account: lowercase latin letters, digits, "_" and "-", up to 40 characters. The AI seller puts the [CARD:code] marker into its reply.
namestring
required
Name. Up to 120 characters.
descriptionstring
required, may be null
Description. Up to 500 characters.
image_urlstring
required, may be null
Image: https:// or the path of a file uploaded to your account storage.
price_textstring
required, may be null
Price as text; when not set — from the product price and currency; null — no price.
badgestring
required, may be null
Badge ("Bestseller"). Up to 30 characters.
page_urlstring
required, may be null
Product page. Only https:// or a path on your site starting with "/" (resolved against the account primary domain).
buttonsarray<CardButton>
required
Up to 3 buttons. Empty — a single "Learn more" button to page_url.
ai_enabledboolean
required
The card is available to the AI seller: code, name and price go into its catalogue. Requires a code.
sortinteger
required
Order in the AI seller catalogue and the operator picker (ascending).
activeboolean
required
The product is active; an inactive card cannot be sent.
created_atstring
required
ISO 8601 UTC.
updated_atstring
required
ISO 8601 UTC.

Examples

Request
curl -X POST 'https://wfacademy.org/api/public/v1/cards' \
  -H 'Authorization: Bearer '"$API_KEY" \
  -H 'Idempotency-Key: '"$(uuidgen)" \
  -H 'Content-Type: application/json' \
  -d '{
  "code": "string",
  "name": "string",
  "description": "string",
  "image_url": "https://example.com/hooks/sapport",
  "page_url": "https://example.com/hooks/sapport",
  "badge": "string",
  "price_text": "string",
  "buttons": [
    {
      "label": "string",
      "url": "https://example.com/hooks/sapport"
    }
  ],
  "ai_enabled": false,
  "sort": 0,
  "active": false
}'
Response 201
{
  "id": "EXAMPLE_ID",
  "code": "string",
  "name": "string",
  "description": "string",
  "image_url": "https://example.com/hooks/sapport",
  "price_text": "string",
  "badge": "string",
  "page_url": "https://example.com/hooks/sapport",
  "buttons": [
    {
      "label": "string",
      "url": "https://example.com/hooks/sapport"
    }
  ],
  "ai_enabled": false,
  "sort": 0,
  "active": false,
  "created_at": "2026-10-11T09:00:00Z",
  "updated_at": "2026-10-11T09:00:00Z"
}
Error example
{
  "type": "https://wfacademy.org/developers/errors#scope_missing",
  "title": "Scope is missing",
  "status": 403,
  "code": "scope_missing",
  "detail": "EXAMPLE",
  "request_id": "req_EXAMPLE"
}

Examples are illustrative: the key in them is a placeholder (EXAMPLE), field values are made up.

Possible errors

invalid_api_key wrong_cell integration_inactive tenant_inactive ip_not_allowed feature_not_in_plan rate_limited wallet_suspended service_unavailable internal_error scope_missing bad_request validation_failed payload_too_large idempotency_key_required idempotency_conflict operation_in_progress

GET /cards/{code} Available

#Get a card

A card by code. Another account card or a missing one — not_found.

Scopes
cards:read
Rate limit
read
Idempotency
not required
Successful response
200 The card.

Parameters

FieldTypeDescription
codestring
required
In: path. The card code.

Response body

FieldTypeDescription
idstring
required
The product id.
codestring
required
The card code, unique in the account: lowercase latin letters, digits, "_" and "-", up to 40 characters. The AI seller puts the [CARD:code] marker into its reply.
namestring
required
Name. Up to 120 characters.
descriptionstring
required, may be null
Description. Up to 500 characters.
image_urlstring
required, may be null
Image: https:// or the path of a file uploaded to your account storage.
price_textstring
required, may be null
Price as text; when not set — from the product price and currency; null — no price.
badgestring
required, may be null
Badge ("Bestseller"). Up to 30 characters.
page_urlstring
required, may be null
Product page. Only https:// or a path on your site starting with "/" (resolved against the account primary domain).
buttonsarray<CardButton>
required
Up to 3 buttons. Empty — a single "Learn more" button to page_url.
ai_enabledboolean
required
The card is available to the AI seller: code, name and price go into its catalogue. Requires a code.
sortinteger
required
Order in the AI seller catalogue and the operator picker (ascending).
activeboolean
required
The product is active; an inactive card cannot be sent.
created_atstring
required
ISO 8601 UTC.
updated_atstring
required
ISO 8601 UTC.

Examples

Request
curl -X GET 'https://wfacademy.org/api/public/v1/cards/EXAMPLE_ID' \
  -H 'Authorization: Bearer '"$API_KEY"
Response 200
{
  "id": "EXAMPLE_ID",
  "code": "string",
  "name": "string",
  "description": "string",
  "image_url": "https://example.com/hooks/sapport",
  "price_text": "string",
  "badge": "string",
  "page_url": "https://example.com/hooks/sapport",
  "buttons": [
    {
      "label": "string",
      "url": "https://example.com/hooks/sapport"
    }
  ],
  "ai_enabled": false,
  "sort": 0,
  "active": false,
  "created_at": "2026-10-11T09:00:00Z",
  "updated_at": "2026-10-11T09:00:00Z"
}
Error example
{
  "type": "https://wfacademy.org/developers/errors#scope_missing",
  "title": "Scope is missing",
  "status": 403,
  "code": "scope_missing",
  "detail": "EXAMPLE",
  "request_id": "req_EXAMPLE"
}

Examples are illustrative: the key in them is a placeholder (EXAMPLE), field values are made up.

Possible errors

invalid_api_key wrong_cell integration_inactive tenant_inactive ip_not_allowed feature_not_in_plan rate_limited wallet_suspended service_unavailable internal_error scope_missing not_found

PATCH /cards/{code} Available

#Update a card

Changes the given fields; pass at least one. Messages already sent do not change — they hold a copy of the card. URLs: https:// or a path on your site ("/…") only; javascript:, data:, http: and another account storage path are rejected (validation_failed).

Scopes
cards:write
Rate limit
write
Idempotency
not required
Successful response
200 The card after the update.

Parameters

FieldTypeDescription
codestring
required
In: path. The card code.

Request body The fields to change.

FieldTypeDescription
codestring
optional
The card code, unique in the account: lowercase latin letters, digits, "_" and "-", up to 40 characters. The AI seller puts the [CARD:code] marker into its reply.
namestring
optional
Name. Up to 120 characters.
descriptionstring
optional, may be null
Description. Up to 500 characters.
image_urlstring
optional, may be null
Image: https:// or the path of a file uploaded to your account storage.
page_urlstring
optional, may be null
Product page. Only https:// or a path on your site starting with "/" (resolved against the account primary domain).
badgestring
optional, may be null
Badge ("Bestseller"). Up to 30 characters.
price_textstring
optional, may be null
Price as text. Up to 40 characters.
buttonsarray<CardButton>
optional
Up to 3 buttons. Empty — a single "Learn more" button to page_url.
ai_enabledboolean
optional
The card is available to the AI seller: code, name and price go into its catalogue. Requires a code.
sortinteger
optional
Order in the AI seller catalogue and the operator picker (ascending).
activeboolean
optional
The product is active; an inactive card cannot be sent.

Response body

FieldTypeDescription
idstring
required
The product id.
codestring
required
The card code, unique in the account: lowercase latin letters, digits, "_" and "-", up to 40 characters. The AI seller puts the [CARD:code] marker into its reply.
namestring
required
Name. Up to 120 characters.
descriptionstring
required, may be null
Description. Up to 500 characters.
image_urlstring
required, may be null
Image: https:// or the path of a file uploaded to your account storage.
price_textstring
required, may be null
Price as text; when not set — from the product price and currency; null — no price.
badgestring
required, may be null
Badge ("Bestseller"). Up to 30 characters.
page_urlstring
required, may be null
Product page. Only https:// or a path on your site starting with "/" (resolved against the account primary domain).
buttonsarray<CardButton>
required
Up to 3 buttons. Empty — a single "Learn more" button to page_url.
ai_enabledboolean
required
The card is available to the AI seller: code, name and price go into its catalogue. Requires a code.
sortinteger
required
Order in the AI seller catalogue and the operator picker (ascending).
activeboolean
required
The product is active; an inactive card cannot be sent.
created_atstring
required
ISO 8601 UTC.
updated_atstring
required
ISO 8601 UTC.

Examples

Request
curl -X PATCH 'https://wfacademy.org/api/public/v1/cards/EXAMPLE_ID' \
  -H 'Authorization: Bearer '"$API_KEY" \
  -H 'Content-Type: application/json' \
  -d '{
  "code": "string",
  "name": "string",
  "description": "string",
  "image_url": "https://example.com/hooks/sapport",
  "page_url": "https://example.com/hooks/sapport",
  "badge": "string",
  "price_text": "string",
  "buttons": [
    {
      "label": "string",
      "url": "https://example.com/hooks/sapport"
    }
  ],
  "ai_enabled": false,
  "sort": 0,
  "active": false
}'
Response 200
{
  "id": "EXAMPLE_ID",
  "code": "string",
  "name": "string",
  "description": "string",
  "image_url": "https://example.com/hooks/sapport",
  "price_text": "string",
  "badge": "string",
  "page_url": "https://example.com/hooks/sapport",
  "buttons": [
    {
      "label": "string",
      "url": "https://example.com/hooks/sapport"
    }
  ],
  "ai_enabled": false,
  "sort": 0,
  "active": false,
  "created_at": "2026-10-11T09:00:00Z",
  "updated_at": "2026-10-11T09:00:00Z"
}
Error example
{
  "type": "https://wfacademy.org/developers/errors#scope_missing",
  "title": "Scope is missing",
  "status": 403,
  "code": "scope_missing",
  "detail": "EXAMPLE",
  "request_id": "req_EXAMPLE"
}

Examples are illustrative: the key in them is a placeholder (EXAMPLE), field values are made up.

Possible errors

invalid_api_key wrong_cell integration_inactive tenant_inactive ip_not_allowed feature_not_in_plan rate_limited wallet_suspended service_unavailable internal_error scope_missing not_found bad_request validation_failed payload_too_large

DELETE /cards/{code} Available

#Delete a card

Removes the card from the product (code, image, buttons, AI seller access); the product itself stays. A repeat — not_found.

Scopes
cards:write
Rate limit
write
Idempotency
not required
Successful response
204 The card is removed; no body.

Parameters

FieldTypeDescription
codestring
required
In: path. The card code.

Examples

Request
curl -X DELETE 'https://wfacademy.org/api/public/v1/cards/EXAMPLE_ID' \
  -H 'Authorization: Bearer '"$API_KEY"
Response 204
HTTP/1.1 204
Error example
{
  "type": "https://wfacademy.org/developers/errors#scope_missing",
  "title": "Scope is missing",
  "status": 403,
  "code": "scope_missing",
  "detail": "EXAMPLE",
  "request_id": "req_EXAMPLE"
}

Examples are illustrative: the key in them is a placeholder (EXAMPLE), field values are made up.

Possible errors

invalid_api_key wrong_cell integration_inactive tenant_inactive ip_not_allowed feature_not_in_plan rate_limited wallet_suspended service_unavailable internal_error scope_missing not_found

POST /conversations/{id}/cards Available PII

#Send cards to a conversation

An operator message with the cards (a copy at the time of sending, URLs resolved). The integration channel gets a message.created event; the site widget shows the cards; Telegram, VK and Max — in their own format; other channels — as text. An unknown or inactive code — validation_failed on /codes. A conversation of another tenant, the student portal or a personal inbox — not_found. A retry with the same Idempotency-Key returns the same message.

Scopes
conversations:write
Rate limit
write
Idempotency
Idempotency-Key is required
Successful response
201 The message is saved.

Parameters

FieldTypeDescription
idstring
required
In: path. The conversation id.
Idempotency-Keystring
required
In: header. A unique string (usually a UUID v4), new for every new operation. A retry with the same key and body yields the same result.

Request body Card codes and a comment.

FieldTypeDescription
codesarray<string>
required
Card codes, 1–3.
commentstring
optional, may be null
Text above the cards, up to 1000 characters.

Response body

FieldTypeDescription
message_idstring
required
The id of the message with the cards.
conversation_idstring
required
created_atstring
required
ISO 8601 UTC.
cardsarray<MessageCard>
required
deliverystring
required
How the cards reach the customer: metadata — the site widget and the integration channel (message.created event); native — Telegram, VK, Max in their own format; text — as "name — price — link" lines.
Values: metadata native text
statusstring
required
Channel delivery state.
Values: sent delivered failed

Examples

Request
curl -X POST 'https://wfacademy.org/api/public/v1/conversations/EXAMPLE_ID/cards' \
  -H 'Authorization: Bearer '"$API_KEY" \
  -H 'Idempotency-Key: '"$(uuidgen)" \
  -H 'Content-Type: application/json' \
  -d '{
  "codes": [
    "string"
  ],
  "comment": "string"
}'
Response 201
{
  "message_id": "EXAMPLE_ID",
  "conversation_id": "EXAMPLE_ID",
  "created_at": "2026-10-11T09:00:00Z",
  "cards": [
    {
      "code": "string",
      "name": "string",
      "description": null,
      "image_url": null,
      "price_text": null,
      "badge": null,
      "page_url": null,
      "buttons": [
        null
      ]
    }
  ],
  "delivery": "metadata",
  "status": "sent"
}
Error example
{
  "type": "https://wfacademy.org/developers/errors#scope_missing",
  "title": "Scope is missing",
  "status": 403,
  "code": "scope_missing",
  "detail": "EXAMPLE",
  "request_id": "req_EXAMPLE"
}

Examples are illustrative: the key in them is a placeholder (EXAMPLE), field values are made up.

Possible errors

invalid_api_key wrong_cell integration_inactive tenant_inactive ip_not_allowed feature_not_in_plan rate_limited wallet_suspended service_unavailable internal_error scope_missing pii_transfer_not_allowed not_found bad_request validation_failed payload_too_large idempotency_key_required idempotency_conflict operation_in_progress