# Coupons for AI Agents: What ACP, UCP and AP2 Say

> What coupons for AI agents are, why there is no standard of their own and how ACP, UCP and AP2 treat discount codes at checkout.

URL: https://clione.ai/glossary/coupons-for-agents/
Lang: en

Coupons for agents is not a new category of coupons or a browser extension that hunts for codes for you. It is the question of what happens to the "Do you have a discount code?" field when the buyer is an [AI agent](/glossary/ai-agent/) and not a person. The short answer: **there is no standard with that name**. What exists are discount extensions inside [agentic commerce](/glossary/agentic-commerce/) protocols, which turn the code into a piece of data in the purchase request and require the store to answer whether it accepts it and, if not, why. It matters to a store because a code rejected silently is a purchase the agent cannot explain to its customer.

## What the protocols say

### ACP: a checkout extension

The [ACP (Agentic Commerce Protocol)](/glossary/acp/) already had basic support: a `coupons` field in requests and the discount detail on each order line. On top of that, its Discount Extension, dated 2026-01-27 and marked as a draft, is **the first extension of the ACP's extension framework**.[^acp-discount-rfc] It arrived with the January 30, 2026 version of the specification, as an optional piece that each implementation adopts when it wants to,[^acp-changelog] and it carries on in the April 17, 2026 stable version.[^acp-discount-examples]

What it defines:[^acp-discount-rfc]

- **The agent sends the codes** in `discounts.codes`. Each submission replaces the previous ones, an empty array removes them all and the store compares them case-insensitively. The old `coupons` stays as a deprecated alias.
- **The store responds with what was applied**: each discount with its coupon (name, percentage or fixed amount), the amount discounted and, if needed, how it is split across the order lines and in what order it stacks with others.
- **Automatic discounts**, the ones the store applies without a code, appear in the same list.
- **Rejected codes** appear separately, with a reason from a closed list, and the store **should** also warn in the session messages with type `warning`, so the user knows they will not get the discount they expected.

There are eight rejection reasons: code expired, not valid, already applied, not combinable with another active discount, minimum purchase not met, user not signed in, user not eligible and usage limit reached.[^acp-discount-rfc] And the specification itself leaves out **the APIs to create and manage discounts, the coupon validation rules and loyalty point redemption**.[^acp-discount-rfc]

A change is in the works, with no published version yet: a field for the agent to say which feed it took the price it showed the buyer from, so the store can honor the catalog price. The policy on when to honor it is the seller's to decide, not the protocol's.[^acp-suggested-price]

### UCP: the same scheme, with automatic discounts that can't be touched

The [UCP (Universal Commerce Protocol)](/glossary/ucp/) has its own extension, `dev.ucp.shopping.discount`, in the August 25, 2026 version of the specification. It lets you send one or several codes, receive the applied discounts with a readable title and amount, and learn about rejected ones through the session messages, with error codes such as expired, not valid or not combinable. It depends on the cart capability, the checkout capability, or both. Automatic discounts appear marked as such, without a code, and **the platform cannot remove them**. And it makes clear who is in charge: **the store decides whether a code is valid**, by its own rules.[^ucp-discount]

Google, in its guide to connecting UCP with [Google AI Mode](/glossary/google-ai-mode/) and [Gemini](/glossary/gemini/), asks the store to declare that capability in its profile in order to receive codes, to report invalid codes as warnings in the messages instead of rejecting the entire request, and to record discounts in the totals as negative values while the amounts in the applied list stay positive.[^google-ucp-promo]

### AP2: the discount is the store's business

[AP2 (Agent Payments Protocol)](/glossary/ap2/) does not define coupons. In its division of roles, the store is **responsible for the integrity of inventory, prices and any discount of its own**.[^ap2-spec] When the agent buys without the person present, with [delegated payments](/glossary/delegated-payments/), the store also has to check that the final order meets all the conditions the person signed off on in advance.[^ap2-spec] A discount that changes the order enters that check like any other change.

### And before paying: promotions in the feed

In the [ChatGPT product feed](/glossary/chatgpt-product-feed/), a markdown is declared with `sale_price`, which has to be greater than zero, lower than the regular price and in the same currency. You can add the period with `sale_price_effective_date`, but OpenAI warns that this date **does not schedule the markdown**: you have to update the feed when it starts and when it ends.[^openai-feed-spec] On Google, [Google Merchant Center](/glossary/google-merchant-center/) promotions predate agents: they show in Google Search, the Shopping tab, Chrome and other surfaces, the United States is among the supported countries, and they have to be redeemable at checkout, last at most 183 days and discount at least $5 or 5%. Its help page does not mention AI Mode.[^gmc-promotions]

## In a store

A **fictional example** store that supports the ACP discount extension. The agent sends two codes when creating the checkout session; one is valid and the other expired. Amounts are in cents, as the specification requires:[^acp-discount-rfc][^acp-discount-examples]

```json
{
  "request": {
    "line_items": [{ "id": "stovetop-espresso-6", "quantity": 1 }],
    "currency": "usd",
    "discounts": { "codes": ["FALL10", "SUMMER25"] }
  },
  "response": {
    "discounts": {
      "codes": ["FALL10", "SUMMER25"],
      "applied": [
        {
          "id": "di_fall10",
          "code": "FALL10",
          "coupon": { "id": "cp_fall10", "name": "10% off in fall", "percent_off": 10 },
          "amount": 399
        }
      ],
      "rejected": [
        {
          "code": "SUMMER25",
          "reason": "discount_code_expired",
          "message": "Code SUMMER25 expired on September 30."
        }
      ]
    },
    "messages": [
      {
        "type": "warning",
        "code": "discount_code_expired",
        "param": "$.discounts.codes[1]",
        "content_type": "plain",
        "content": "Code SUMMER25 expired on September 30."
      }
    ]
  }
}
```

What the agent can tell its customer comes from there: 10% was applied, **the second code was not, because it expired**, and with a date. Without the `rejected` block and the warning, the agent would only see a total higher than it expected.


Believing that putting dates on a markdown in the feed turns it on and off by itself. In OpenAI's feed, `sale_price_effective_date` is accepted as data, but **it does not schedule the markdown**: if you don't update the feed when the promotion ends, the agent keeps seeing the discounted price.[^openai-feed-spec] And then, at checkout, the store may not honor it.


## How to check it

1. **Ask your platform or payments provider** whether their ACP or UCP implementation declares the discount extension. In the ACP it appears in the extensions of the checkout response;[^acp-discount-rfc] in the UCP, as `dev.ucp.shopping.discount` in the profile.[^ucp-discount]
2. **If you have a UCP profile, open it** at `https://your-domain/.well-known/ucp` and look for that capability. Without it, Google does not send you codes.[^google-ucp-promo]
3. **Test your tricky codes**: an expired one, one with a minimum purchase and one that can't be combined. Each rejection should come back with its reason, not as a generic error.[^acp-discount-rfc]
4. **Review your feed when each promotion ends**: the discounted price has to disappear when it is over.[^openai-feed-spec]
5. **If you use Merchant Center promotions**, check that they meet its duration and minimum discount requirements.[^gmc-promotions]

## Related concept: agentic checkout

[Agentic checkout](/glossary/agentic-checkout/) is the payment stage when an agent does it, and coupons live inside it: **in the ACP and the UCP, the discount is an extension of the checkout session**, not a separate protocol.[^acp-discount-rfc][^ucp-discount] Before payment, what the agent knows about a markdown is what your feed says; that belongs to [AI product discovery](/glossary/ai-product-discovery/). And who decides to use a code, the agent alone or the person, depends on whether the agent is [autonomous or assisted](/glossary/autonomous-vs-assisted-agents/).

To go further, the [agentic commerce reading path](/learn/agentic-commerce/) orders the protocols that take an agent from catalog to payment.
