> ## Documentation Index
> Fetch the complete documentation index at: https://docs.alura.io/llms.txt
> Use this file to discover all available pages before exploring further.

# Replace inventory

> Replace the whole inventory of one listing on Etsy: its variants, each variant's SKU, price, quantity and processing profile, and which properties set them.

**Cost:** 1 API credit per write.

```bash
curl -X PUT "https://api.alura.io/v1/workspace/listings/1834720561/inventory" \
  -H "Authorization: Bearer $ALURA_API_KEY" \
  -H "Content-Type: application/json" \
  -H "Idempotency-Key: $(uuidgen)" \
  -d '{
    "products": [
      {"sku": "MUG-NAME-11", "property_values": [{"property_id": "200", "property_name": "Primary color", "values": ["White"], "value_ids": ["6301"]}],
       "offerings": [{"price": "18.50", "quantity": 20, "is_enabled": true, "processing_profile_id": "4601"}]},
      {"sku": "MUG-NAME-11-BLK", "property_values": [{"property_id": "200", "property_name": "Primary color", "values": ["Black"], "value_ids": ["6302"]}],
       "offerings": [{"price": "21.00", "quantity": 15, "is_enabled": true, "processing_profile_id": "4601"}]}
    ],
    "price_on_property": ["200"],
    "quantity_on_property": ["200"],
    "sku_on_property": ["200"]
  }'
```

Changes the live listing on Etsy. Needs the `listings:write` scope and the **Listing optimization** workspace permission. Send `dry_run=true` to see the planned write and its range of Etsy calls without sending it.

A listing has one product per combination of variation values. Each product has a SKU and one offering: price, quantity, enabled, and processing profile.

> [!WARNING]
>
> This is a full replace, like Etsy's own inventory write. A product you leave out is removed from the listing. A `price_on_property`, `quantity_on_property`, `sku_on_property` or `processing_profile_on_property` you leave out is cleared. Read the current inventory with [Get listing](https://docs.alura.io/api-reference/workspace/listings/get.md) and `expand=inventory`, and send back every product you want to keep.

To change a few variants without restating the rest, use [Patch offerings](https://docs.alura.io/api-reference/workspace/listings/inventory/patch.md).

## Add or remove variations

* Adding a product adds a variation value.
* Removing every product of a value removes the value, and with it the value's variation images on Etsy.
* `property_id` is a category property from [Get category properties](https://docs.alura.io/api-reference/etsy/categories/properties.md), or `513` and `514` for the shop's own variations.
* Every offering of a physical listing needs a `processing_profile_id`. Without one, the answer is `400` before anything is sent.

> [!NOTE]
>
> Etsy can issue new product and offering IDs on any inventory write, and does when variants are added or removed. Never keep them to address a variant: select variants by their property values with [Patch offerings](https://docs.alura.io/api-reference/workspace/listings/inventory/patch.md).

## The answer

| Answer | Meaning | What to do |
| - | - | - |
| `200` | The write landed. The body is the inventory as Etsy returned it, with Etsy's new IDs, and its `change`. | Nothing. |
| `202` | Etsy is still answering, or Alura is checking whether it landed. The body is the change. | Poll [Get change](https://docs.alura.io/api-reference/workspace/changes/get.md) at `Location`. Don't send the write again. |
| `409 listing_busy` | Another inventory write to this listing is running. Only one runs at a time. | Retry after `Retry-After`. |

Send an `Idempotency-Key` with every write: a retry under the same key answers from the first write and never writes twice. See [Idempotency](https://docs.alura.io/api-reference/introduction.md#idempotency).

## Undo a change

[Revert change](https://docs.alura.io/api-reference/workspace/changes/revert.md) restores the prices, SKUs and enabled flags. It never restores quantities or variation images, and a change that added or removed variants can't be reverted.

The [inventory guide](https://docs.alura.io/guides/your-shop-inventory.md) walks through a full replace. [Credits and limits](https://docs.alura.io/api-reference/credits-and-limits.md) says when a write is charged.


## OpenAPI

````yaml /openapi.json put /v1/workspace/listings/{id}/inventory
openapi: 3.1.0
info:
  title: Alura API
  version: 1.0.0
  description: Etsy market research for scripts and AI assistants.
servers:
  - url: https://api.alura.io
security:
  - apiKey: []
paths:
  /v1/workspace/listings/{id}/inventory:
    put:
      summary: Replace inventory
      description: >-
        Replaces the whole inventory of one listing of your connected Etsy shops
        on Etsy: its products (one per combination of variation values), each
        product's SKU and offering (price, quantity, enabled, processing
        profile), and which properties set the price, quantity, SKU and
        processing profile per variant (`*_on_property`). Full replace, as
        Etsy's own inventory write: a product you leave out is removed from the
        listing, and a `*_on_property` you leave out is cleared, so send every
        product you want to keep (GET
        /v1/workspace/listings/{id}?expand=inventory shows the current ones).
        Adding a product adds a variation value; removing every product of a
        value removes it, and with it the value's variation images on Etsy (a
        revert does not restore variation images). Every offering of a physical
        listing needs a `processing_profile_id` (400 before anything is sent).
        To change a few variants without restating the rest, use Patch
        offerings. Etsy can issue new product and offering IDs on any inventory
        write (it does when variants are added or removed): never keep them to
        address a variant; patch offerings by their property values. One
        inventory write runs at a time per listing: another is 409
        `listing_busy`. Answers 200 with the inventory as Etsy returned it and
        the change, or 202 with the change while Etsy is still answering or
        Alura is checking whether it landed; `dry_run=true` shows the planned
        write and its Etsy-call range. A revert of the change restores prices,
        SKUs and enabled flags, never quantities. Needs the `listings:write`
        scope and the Listing optimization workspace permission. Costs 1 API
        credit when the change lands on Etsy, nothing when it is refused;
        `dry_run` is free.


        Cost: 1 API credit per write.
      operationId: workspace.listings.inventory.replace
      parameters:
        - name: id
          in: path
          required: true
          schema:
            description: The Etsy listing ID. A listing outside the workspace is 404.
            type: string
            pattern: ^[0-9]{1,20}$
            example: '1834720561'
        - name: dry_run
          in: query
          required: false
          description: >-
            `true`: plan the write and send nothing: what it would change, the
            Etsy calls it would make, and nothing reserved, charged or recorded.
            Free; counts toward the per-minute write limit.
          schema:
            type: boolean
        - name: Idempotency-Key
          in: header
          required: false
          description: >-
            Makes a retry safe: the same key with the same request within 24
            hours answers from the first write (with `Idempotent-Replayed:
            true`) and never writes to Etsy twice; a write that failed with
            nothing written (`Retry-After` set) is tried again under it. The
            same key with a different request is a 409 `conflict`; while the
            first request still runs, 409 `idempotency_processing` (or the same
            202). Required for relative changes such as `adjust_price`, and to
            add a listing file, image or video, or to change the alt text of an
            image (each uploads to Etsy, so a blind retry would upload again); a
            `dry_run=true` needs none.
          schema:
            type: string
            minLength: 1
            maxLength: 255
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              properties:
                products:
                  minItems: 1
                  maxItems: 400
                  type: array
                  items:
                    type: object
                    properties:
                      sku:
                        type: string
                        maxLength: 32
                        description: The product's SKU, at most 32 characters; "" for none.
                      property_values:
                        maxItems: 2
                        type: array
                        items:
                          type: object
                          properties:
                            property_id:
                              type: string
                              pattern: ^[1-9][0-9]{0,18}$
                              description: >-
                                Etsy's property ID: a category property (GET
                                /v1/etsy/categories/{id}/properties), or 513 /
                                514 for the shop's own variations.
                            property_name:
                              type: string
                              minLength: 1
                              maxLength: 45
                              description: >-
                                The property's name, for example "Size" or
                                "Primary color". Patch selectors match it.
                            values:
                              minItems: 1
                              maxItems: 1
                              type: array
                              items:
                                type: string
                                minLength: 1
                                maxLength: 45
                              description: >-
                                The one value of this property for the product,
                                for example ["A4"].
                            value_ids:
                              description: >-
                                Etsy's ID of the value, when the category
                                property has one; Etsy assigns one otherwise.
                              maxItems: 1
                              type: array
                              items:
                                type: string
                                pattern: ^[1-9][0-9]{0,18}$
                            scale_id:
                              description: >-
                                Etsy's scale of the value (a size system, a
                                unit), when the property has scales.
                              type: string
                              pattern: ^[1-9][0-9]{0,18}$
                          required:
                            - property_id
                            - property_name
                            - values
                          additionalProperties: false
                        description: >-
                          The product's variation values, one per property; []
                          for a listing without variations (then send one
                          product).
                      offerings:
                        minItems: 1
                        maxItems: 1
                        type: array
                        items:
                          type: object
                          properties:
                            price:
                              description: >-
                                The offering's price in the listing's own
                                currency, as a decimal string such as "24.99" (a
                                number with at most 2 decimals is accepted too);
                                at least 0.20.
                              type:
                                - string
                                - number
                            quantity:
                              type: integer
                              minimum: 0
                              maximum: 999
                              description: The offering's quantity in stock, 0-999.
                            is_enabled:
                              type: boolean
                              description: >-
                                false: the variant is shown as unavailable on
                                Etsy.
                            processing_profile_id:
                              description: >-
                                A processing profile of the listing's shop (GET
                                /v1/workspace/processing-profiles). Etsy needs
                                one on every offering of a physical listing; a
                                profile of another shop is 404.
                              type: string
                              pattern: ^[1-9][0-9]{0,18}$
                          required:
                            - price
                            - quantity
                            - is_enabled
                          additionalProperties: false
                        description: The product's offering (Etsy has one per product).
                    required:
                      - property_values
                      - offerings
                    additionalProperties: false
                  description: >-
                    Every product of the listing, 1-400: a product left out is
                    removed from the listing.
                price_on_property:
                  description: >-
                    The properties whose values set the price (each must be a
                    property of the products); empty or left out: one price for
                    every variant.
                  maxItems: 2
                  type: array
                  items:
                    type: string
                    pattern: ^[1-9][0-9]{0,18}$
                quantity_on_property:
                  description: >-
                    The properties whose values set the quantity (each must be a
                    property of the products); empty or left out: one quantity
                    for every variant.
                  maxItems: 2
                  type: array
                  items:
                    type: string
                    pattern: ^[1-9][0-9]{0,18}$
                sku_on_property:
                  description: >-
                    The properties whose values set the SKU (each must be a
                    property of the products); empty or left out: one SKU for
                    every variant.
                  maxItems: 2
                  type: array
                  items:
                    type: string
                    pattern: ^[1-9][0-9]{0,18}$
                processing_profile_on_property:
                  description: >-
                    The properties whose values set the processing profile (each
                    must be a property of the products); empty or left out: one
                    processing profile for every variant.
                  maxItems: 2
                  type: array
                  items:
                    type: string
                    pattern: ^[1-9][0-9]{0,18}$
              required:
                - products
              additionalProperties: false
            example:
              products:
                - sku: MUG-NAME-11
                  property_values:
                    - property_id: '200'
                      property_name: Primary color
                      values:
                        - White
                      value_ids:
                        - '6301'
                  offerings:
                    - price: '18.50'
                      quantity: 20
                      is_enabled: true
                      processing_profile_id: '4601'
                - sku: MUG-NAME-11-BLK
                  property_values:
                    - property_id: '200'
                      property_name: Primary color
                      values:
                        - Black
                      value_ids:
                        - '6302'
                  offerings:
                    - price: '21.00'
                      quantity: 15
                      is_enabled: true
                      processing_profile_id: '4601'
              price_on_property:
                - '200'
              quantity_on_property:
                - '200'
              sku_on_property:
                - '200'
      responses:
        '200':
          description: >-
            OK: the write landed on Etsy (or, with `dry_run=true`, what it would
            do).
          headers:
            Request-Id:
              $ref: '#/components/headers/Request-Id'
            Alura-Credits-Cost:
              $ref: '#/components/headers/Alura-Credits-Cost'
            Alura-Credits-Remaining:
              $ref: '#/components/headers/Alura-Credits-Remaining'
            Idempotent-Replayed:
              description: '`true` when this answers an earlier request with the same key.'
              schema:
                type: string
            Alura-Write-Budget-Remaining:
              description: The shop's Etsy write budget left, when known.
              schema:
                type: integer
            Alura-Write-Deduplicated:
              description: >-
                Set when this write was answered, free, from an earlier
                identical write: that write's change id (`chn_...`). Nothing was
                sent to Etsy again.
              schema:
                type: string
          content:
            application/json:
              schema:
                anyOf:
                  - type: object
                    properties:
                      object:
                        type: string
                        const: workspace.listing_inventory
                      listing_id:
                        type: string
                        description: Etsy ID, as a string.
                      shop_id:
                        type: string
                        description: Etsy ID, as a string.
                      products:
                        anyOf:
                          - type: array
                            items:
                              type: object
                              properties:
                                id:
                                  type: string
                                  description: >-
                                    Etsy's product ID. Etsy can issue a new one
                                    on any inventory write (it did whenever
                                    variants were added or removed; a SKU-only
                                    patch kept them, live 2026-10-23): never
                                    keep it to address a variant; select by
                                    property values.
                                sku:
                                  description: >-
                                    The SKU; "" when the product has none, null
                                    when Etsy did not say.
                                  type:
                                    - string
                                    - 'null'
                                property_values:
                                  type: array
                                  items:
                                    type: object
                                    properties:
                                      property_id:
                                        type: string
                                        description: Etsy ID, as a string.
                                      property_name:
                                        description: >-
                                          The property's name, for example `Size`;
                                          null when Etsy did not say.
                                        type:
                                          - string
                                          - 'null'
                                      scale_id:
                                        anyOf:
                                          - type: string
                                            description: Etsy ID, as a string.
                                          - type: 'null'
                                        description: >-
                                          Etsy's scale of the value (a size
                                          system, a unit); null when none.
                                      value_ids:
                                        type: array
                                        items:
                                          type: string
                                          description: Etsy ID, as a string.
                                        description: Etsy's IDs of the values.
                                      values:
                                        type: array
                                        items:
                                          type: string
                                        description: The values by name, for example `A4`.
                                    required:
                                      - property_id
                                      - property_name
                                      - scale_id
                                      - value_ids
                                      - values
                                    additionalProperties: false
                                  description: >-
                                    The product's variation values, one per
                                    property; empty without variations.
                                offerings:
                                  type: array
                                  items:
                                    type: object
                                    properties:
                                      id:
                                        type: string
                                        description: >-
                                          Etsy's offering ID; it can change on any
                                          inventory write too.
                                      price:
                                        anyOf:
                                          - type: object
                                            properties:
                                              amount:
                                                type: string
                                                description: >-
                                                  Decimal string in the listing's own
                                                  currency.
                                              currency:
                                                type: string
                                                description: ISO 4217 code.
                                              usd:
                                                description: >-
                                                  The same price in USD; null unless the
                                                  listing is priced in USD (no exchange
                                                  rate is read after a write).
                                                type:
                                                  - string
                                                  - 'null'
                                            required:
                                              - amount
                                              - currency
                                              - usd
                                            additionalProperties: false
                                          - type: 'null'
                                        description: >-
                                          The offering's price as Etsy answered;
                                          null when Etsy did not say.
                                      quantity:
                                        anyOf:
                                          - type: integer
                                          - type: 'null'
                                        description: >-
                                          The offering's quantity in stock; null
                                          when Etsy did not say.
                                      is_enabled:
                                        description: >-
                                          false: the variant is shown as
                                          unavailable on Etsy; null when Etsy did
                                          not say.
                                        type:
                                          - boolean
                                          - 'null'
                                      processing_profile_id:
                                        anyOf:
                                          - type: string
                                            description: Etsy ID, as a string.
                                          - type: 'null'
                                        description: >-
                                          The offering's processing profile; null
                                          for a digital offering, or when Etsy did
                                          not say.
                                    required:
                                      - id
                                      - price
                                      - quantity
                                      - is_enabled
                                      - processing_profile_id
                                    additionalProperties: false
                                  description: >-
                                    The product's offering (Etsy has one per
                                    product).
                              required:
                                - id
                                - sku
                                - property_values
                                - offerings
                              additionalProperties: false
                          - type: 'null'
                        description: >-
                          Every product as Etsy answered the write, with Etsy's
                          new IDs; null when Etsy's answer carried none (notice
                          `inventory_not_returned`).
                      price_on_property:
                        anyOf:
                          - type: array
                            items:
                              type: string
                              description: Etsy ID, as a string.
                          - type: 'null'
                        description: >-
                          The properties whose values set the price; [] for one
                          price for every variant; null when Etsy did not say.
                      quantity_on_property:
                        anyOf:
                          - type: array
                            items:
                              type: string
                              description: Etsy ID, as a string.
                          - type: 'null'
                        description: >-
                          The properties whose values set the quantity; [] for
                          one quantity for every variant; null when Etsy did not
                          say.
                      sku_on_property:
                        anyOf:
                          - type: array
                            items:
                              type: string
                              description: Etsy ID, as a string.
                          - type: 'null'
                        description: >-
                          The properties whose values set the SKU; [] for one
                          SKU for every variant; null when Etsy did not say.
                      processing_profile_on_property:
                        anyOf:
                          - type: array
                            items:
                              type: string
                              description: Etsy ID, as a string.
                          - type: 'null'
                        description: >-
                          The properties whose values set the processing
                          profile; [] for one profile for every variant; null
                          when Etsy did not say.
                      as_of:
                        type: string
                        description: When Etsy answered the write.
                      change:
                        type: object
                        properties:
                          id:
                            type: string
                            description: >-
                              `chn_...`: GET /v1/workspace/changes/{id} shows
                              it.
                          status:
                            type: string
                            const: succeeded
                            description: >-
                              Always `succeeded`: an inventory write lands whole
                              or not at all.
                          applied_fields:
                            type: array
                            items:
                              type: string
                            description: '`inventory`.'
                          failed_fields:
                            type: array
                            items:
                              type: object
                              properties:
                                field:
                                  type: string
                                  description: The part that did not land.
                                code:
                                  type: string
                                  description: Why it did not land.
                              required:
                                - field
                                - code
                              additionalProperties: false
                            description: >-
                              Always empty: an inventory write is one Etsy call,
                              which lands whole or not at all.
                        required:
                          - id
                          - status
                          - applied_fields
                          - failed_fields
                        additionalProperties: false
                        description: 'The write: its change ID and what landed.'
                      notices:
                        type: array
                        items:
                          type: object
                          properties:
                            code:
                              type: string
                              description: >-
                                `inventory_not_returned`. New codes may be
                                added.
                            detail:
                              type: string
                              description: What the notice means for this answer.
                          required:
                            - code
                            - detail
                          additionalProperties: false
                        description: >-
                          Why a part of the answer is unknown; empty when
                          nothing is.
                    required:
                      - object
                      - listing_id
                      - shop_id
                      - products
                      - price_on_property
                      - quantity_on_property
                      - sku_on_property
                      - processing_profile_on_property
                      - as_of
                      - change
                      - notices
                    additionalProperties: false
                  - type: object
                    properties:
                      object:
                        type: string
                        const: workspace.write_plan
                      operation:
                        type: string
                        description: The operation this plan is for.
                      target:
                        type: object
                        properties:
                          type:
                            type: string
                            description: >-
                              What the write changes: `listing`, `shop`,
                              `receipt`. New types may be added.
                          id:
                            type: string
                            description: Etsy ID, as a string.
                          shop_id:
                            type: string
                            description: Etsy ID, as a string.
                        required:
                          - type
                          - id
                          - shop_id
                        additionalProperties: false
                        description: What the write would change.
                      changes:
                        type: array
                        items:
                          type: object
                          properties:
                            field:
                              type: string
                              description: The field, named as in the resource.
                            to:
                              description: The value it would be set to.
                          required:
                            - field
                            - to
                          additionalProperties: false
                        description: What the write would set, field by field.
                      command_hash:
                        type: string
                        pattern: ^[0-9a-f]{64}$
                        description: >-
                          A hash of the change Alura would send to Etsy: the
                          same request on the same object plans the same change,
                          whatever Alura has stored about it.
                      estimate:
                        type: object
                        properties:
                          etsy_calls_min:
                            type: integer
                            minimum: 0
                            description: The fewest Etsy calls the write makes.
                          etsy_calls_max:
                            type: integer
                            minimum: 0
                            description: >-
                              The most Etsy calls the write makes, counting its
                              token refreshes and every call Alura may send
                              again (after a timeout, an Etsy 409 conflict, a
                              rejected token or a video re-association's 5xx);
                              only the calls it sends again after Etsy answers
                              429 (rate limited) are not counted.
                        required:
                          - etsy_calls_min
                          - etsy_calls_max
                        additionalProperties: false
                        description: Etsy calls the write would make, as a range.
                      write_budget_remaining:
                        anyOf:
                          - type: integer
                            minimum: 0
                          - type: 'null'
                        description: >-
                          The shop's Etsy calls left in its rolling 24-hour
                          write budget, as of Alura's last count; null when
                          unknown (a dry run does not ask Etsy).
                      consequential:
                        type: boolean
                        description: >-
                          Whether the write needs a confirmation token over MCP
                          (today: every write documented here).
                      confirmation_token:
                        description: >-
                          Over MCP, for a consequential write: pass it as
                          `confirmation_token` on the write itself, after the
                          user confirmed. Valid 10 minutes, once. Null
                          otherwise.
                        type:
                          - string
                          - 'null'
                      confirmation_expires_at:
                        description: >-
                          When the confirmation token expires (ISO 8601, UTC);
                          null without one.
                        type:
                          - string
                          - 'null'
                      notices:
                        type: array
                        items:
                          type: object
                          properties:
                            code:
                              type: string
                              description: >-
                                `write_budget_stale`: Alura's last count of the
                                write budget is from before its window moved on,
                                so `write_budget_remaining` is null.
                                `not_reverted`: a revert leaves a field of the
                                change as it is (its detail says which and why).
                                New codes may be added.
                            detail:
                              type: string
                          required:
                            - code
                            - detail
                          additionalProperties: false
                        description: >-
                          Why a part of the plan is unknown; empty when nothing
                          is.
                    required:
                      - object
                      - operation
                      - target
                      - changes
                      - command_hash
                      - estimate
                      - write_budget_remaining
                      - consequential
                      - confirmation_token
                      - confirmation_expires_at
                      - notices
                    additionalProperties: false
              example:
                object: workspace.listing_inventory
                listing_id: '1834720561'
                shop_id: '22841907'
                products:
                  - id: '6111'
                    sku: MUG-NAME-11
                    property_values:
                      - property_id: '200'
                        property_name: Primary color
                        scale_id: null
                        value_ids:
                          - '6301'
                        values:
                          - White
                    offerings:
                      - id: '6211'
                        price:
                          amount: '18.50'
                          currency: USD
                          usd: '18.50'
                        quantity: 20
                        is_enabled: true
                        processing_profile_id: '4601'
                  - id: '6112'
                    sku: MUG-NAME-11-BLK
                    property_values:
                      - property_id: '200'
                        property_name: Primary color
                        scale_id: null
                        value_ids:
                          - '6302'
                        values:
                          - Black
                    offerings:
                      - id: '6212'
                        price:
                          amount: '21.00'
                          currency: USD
                          usd: '21.00'
                        quantity: 15
                        is_enabled: true
                        processing_profile_id: '4601'
                price_on_property:
                  - '200'
                quantity_on_property: []
                sku_on_property:
                  - '200'
                processing_profile_on_property: []
                as_of: '2026-10-17T12:00:00.000Z'
                change:
                  id: chn_01JMOCK0000000000000000000
                  status: succeeded
                  applied_fields:
                    - inventory
                  failed_fields: []
                notices: []
        '202':
          description: >-
            Accepted: the write is still being applied on Etsy, or its outcome
            is being checked. Poll the change at `Location`.
          headers:
            Request-Id:
              $ref: '#/components/headers/Request-Id'
            Alura-Credits-Cost:
              $ref: '#/components/headers/Alura-Credits-Cost'
            Alura-Credits-Remaining:
              $ref: '#/components/headers/Alura-Credits-Remaining'
            Location:
              description: 'The change to poll: `/v1/workspace/changes/{id}`.'
              schema:
                type: string
            Retry-After:
              description: Seconds to wait before polling.
              schema:
                type: integer
            Idempotent-Replayed:
              description: '`true` when this answers an earlier request with the same key.'
              schema:
                type: string
            Alura-Write-Deduplicated:
              description: >-
                Set when this write was answered, free, from an earlier
                identical write: that write's change id (`chn_...`). Nothing was
                sent to Etsy again.
              schema:
                type: string
          content:
            application/json:
              schema:
                type: object
                properties:
                  object:
                    type: string
                    const: workspace.change
                  id:
                    type: string
                    description: >-
                      `chn_` + the change's number (a change made in Alura), or
                      `chn_` + a write's 26-character ID (a change made through
                      the API).
                  shop_id:
                    type: string
                    description: The connected shop the change was made in.
                  target:
                    type: object
                    properties:
                      type:
                        type: string
                        description: >-
                          What was changed: `listing`, `shop`, `receipt` or a
                          shop setting (`section`, `return_policy`,
                          `shipping_profile`, ...). New types may be added.
                      id:
                        type: string
                        description: Etsy ID, as a string.
                    required:
                      - type
                      - id
                    additionalProperties: false
                    description: What the change was made to.
                  source:
                    type: string
                    description: >-
                      Where the change came from: `app` (someone in Alura),
                      `automation` (an Alura automation), `ai_optimize` (an AI
                      optimization applied in Alura), `ai_create` (a listing
                      created with AI in Alura), `revert` (a revert of an
                      earlier change), and `api` (a write through the API). New
                      values may be added.
                  actor:
                    anyOf:
                      - type: object
                        properties:
                          type:
                            type: string
                            description: >-
                              `user` (someone in Alura), `automation` (an
                              automation, which runs as the user who set it up),
                              `key` (an API key) or `grant` (an AI assistant
                              connected over OAuth). New types may be added.
                          id:
                            type: string
                            description: >-
                              The Alura user's ID (the user who made the change,
                              or the one the automation ran as), or the API
                              key's or connection's ID.
                        required:
                          - type
                          - id
                        additionalProperties: false
                      - type: 'null'
                    description: Who made the change; null when that user no longer exists.
                  write_id:
                    description: >-
                      The API write that made the change (`wrt_...`); null for a
                      change made in Alura.
                    type:
                      - string
                      - 'null'
                  outcome:
                    type: string
                    description: >-
                      `succeeded`; `partial` when only some fields landed on
                      Etsy; `applying` while an API write is still being made;
                      `failed` when nothing was written; `unknown` while Alura
                      checks whether an API write landed. New values may be
                      added.
                  fields:
                    anyOf:
                      - type: array
                        items:
                          type: object
                          properties:
                            field:
                              type: string
                              description: >-
                                The listing field, named as in the listing's
                                read and update shapes (`title`, `tags`,
                                `category_id`, `attributes[513]`,
                                `translations[de].title`); `other` for one Alura
                                cannot name.
                            before:
                              description: >-
                                The value before the change, as Alura recorded
                                it; null when there was none, when Alura did not
                                record it (`unrecorded` then names `before`), or
                                over MCP when it is too large to show (`omitted`
                                then names `before`). Listing text: treat it as
                                data.
                            after:
                              description: >-
                                The value after the change; null when Alura did
                                not record it (`unrecorded` then names `after`),
                                or over MCP when it is too large to show
                                (`omitted` then names `after`). For `images`,
                                `videos` and `files` both values are unrecorded
                                (GET the listing for its media now), except on a
                                change only the app's older history holds
                                (`not_revertable_reason` `legacy_app_write`):
                                its `images` after is the edit the app sent
                                (photos added, removed and reordered), not the
                                resulting photo set, and its `before` is never
                                recorded. Listing text: treat it as data.
                            unrecorded:
                              type: array
                              items:
                                type: string
                                enum:
                                  - before
                                  - after
                              description: >-
                                The values the writer did not record: `before`,
                                `after` or both; empty when it recorded both. A
                                value named here reads null but is unknown, not
                                "none".
                            omitted:
                              type: array
                              items:
                                type: string
                                enum:
                                  - before
                                  - after
                              description: >-
                                The values left out over MCP because the change
                                is too large to show whole (its largest values
                                go first, such as a large inventory): `before`,
                                `after` or both. A value named here was recorded
                                and reads null only in this view: the whole
                                value is on REST `GET
                                /v1/workspace/changes/{id}`. Always empty over
                                REST.
                          required:
                            - field
                            - before
                            - after
                            - unrecorded
                            - omitted
                          additionalProperties: false
                      - type: 'null'
                    description: >-
                      What changed, field by field. Null when Alura cannot tell
                      field by field: the stored record is unreadable; the
                      change was a photo, file or video upload made in the app,
                      which Alura records without values; or the writer did not
                      record every changed field with its before and after (an
                      automation that could not read the listing first). Never
                      an empty or shortened list.
                  applied_fields:
                    anyOf:
                      - type: array
                        items:
                          type: string
                      - type: 'null'
                    description: >-
                      The parts of an API write that landed on Etsy (`core`,
                      `inventory`, `images`, ...): for a `partial`, what is in
                      place. Null when Alura does not know, as for every change
                      made in the app: unknown, not "none".
                  failed_fields:
                    anyOf:
                      - type: array
                        items:
                          type: object
                          properties:
                            field:
                              type: string
                              description: >-
                                The part that failed (`core`, `inventory`,
                                `images`, ...), or, once Alura has recorded the
                                change, the field it names (`images[77]`,
                                `translations[de]`).
                            code:
                              description: >-
                                Why it failed, as Alura's error code
                                (`etsy_error`, ...): `outcome_unknown` when the
                                answer from Etsy for this part was lost, so it
                                may have applied (check the listing on Etsy
                                before writing it again); `activation_skipped`
                                for a publish (`activate`) held back because
                                another part failed. Null when Alura has no code
                                for it (the write's own record, before or
                                without its full change record). New values may
                                be added.
                              type:
                                - string
                                - 'null'
                          required:
                            - field
                            - code
                          additionalProperties: false
                      - type: 'null'
                    description: >-
                      The parts of an API write that failed, each with its error
                      code: for a `partial`, what to finish with a new write.
                      Null when Alura does not know, as for every change made in
                      the app: unknown, not "none".
                  before_source:
                    description: >-
                      Where `before` came from: `live` (read from Etsy during
                      the write) or `cache` (Alura's copy); null when unknown,
                      as for every change made in the app.
                    type:
                      - string
                      - 'null'
                  before_as_of:
                    anyOf:
                      - type: string
                        description: ISO 8601, UTC.
                      - type: 'null'
                    description: When `before` was current; null when unknown.
                  event:
                    description: >-
                      What kind of change: `edited`, `created`, `published`,
                      `deleted`, `reverted`, `shipment_added`, `shop_updated`,
                      `settings_created`, `settings_updated`,
                      `settings_deleted`. Null while an API write is still being
                      made. New values may be added.
                    type:
                      - string
                      - 'null'
                  revertable:
                    type: boolean
                    description: >-
                      Whether `POST /v1/workspace/changes/{id}/revert` can undo
                      it (at least one field): a change Alura made through its
                      change log with `before` read live from Etsy, whose core
                      fields, inventory prices, SKUs or enabled flags,
                      attributes, translations or personalization landed.
                      Reverting checks the listing on Etsy again first (`409
                      changed_since` when it moved).
                  not_revertable_reason:
                    description: >-
                      Why none of it can be reverted: `legacy_app_write` (a
                      change recorded only by the app: history only),
                      `before_from_cache` (`before` came from Alura's copy, not
                      Etsy), `before_unrecorded`, `after_unrecorded`,
                      `not_landed` (its core fields did not land),
                      `outcome_unknown` (whether it landed is not known: its
                      outcome is `unknown` or `applying`, or a `partial` without
                      its applied parts recorded; it may have), `delete`,
                      `publish_fee` (undoing a publish is not free on Etsy),
                      `shipment_notified_buyer` (Etsy emailed the buyer),
                      `images`, `files` (a digital file added or removed: the
                      API keeps no copy of a file), `quantity` (never restored
                      from a snapshot: oversell risk), `reactivates_listing` (it
                      would put the listing back on sale), `target_not_listing`
                      (shop changes; a shop setting's change is `delete` once
                      Alura has recorded that it deleted the setting, else
                      `not_supported`), `not_supported` (a field or part the API
                      cannot restore yet), `etsy_updated_at_unrecorded` (the
                      updated time of the listing on Etsy after the change was
                      not recorded, so Alura's record of it is incomplete),
                      `needs_production_partners` (`who_made: someone_else`
                      cannot be restored without production partners, which a
                      revert never restores), `field_unrecorded` (the change did
                      not record a value it wrote), `translation_added` (the
                      change created a translation, and Etsy has no translation
                      delete), `variations_changed` (an inventory change that
                      added or removed variants, or moved which property sets
                      the price or SKU), `reference_deleted` (the section,
                      shipping profile or return policy it would put back has
                      been deleted since), `revertability_unknown` (on a write's
                      own answer only, when Alura could not read its change
                      record just then: GET /v1/workspace/changes/{id} answers
                      it). Null when it can. New values may be added.
                    type:
                      - string
                      - 'null'
                  reverts:
                    description: >-
                      For a change with `source: revert`: the id of the change
                      it undid (`chn_...`). Null otherwise, and on the
                      `workspace.change` a revert answers with while Etsy is
                      still answering (GET /v1/workspace/changes/{id} has it
                      once the revert is recorded).
                    type:
                      - string
                      - 'null'
                  created_at:
                    type: string
                    description: When the change was made.
                  as_of:
                    type: string
                    description: When this record was read.
                required:
                  - object
                  - id
                  - shop_id
                  - target
                  - source
                  - actor
                  - write_id
                  - outcome
                  - fields
                  - applied_fields
                  - failed_fields
                  - before_source
                  - before_as_of
                  - event
                  - revertable
                  - not_revertable_reason
                  - reverts
                  - created_at
                  - as_of
                additionalProperties: false
        '400':
          $ref: '#/components/responses/WriteProblem400'
        '401':
          $ref: '#/components/responses/Problem401'
        '402':
          $ref: '#/components/responses/WriteProblem402'
        '403':
          $ref: '#/components/responses/WriteProblem403'
        '404':
          $ref: '#/components/responses/WriteProblem404'
        '405':
          $ref: '#/components/responses/Problem405'
        '409':
          $ref: '#/components/responses/WriteProblem409'
        '410':
          $ref: '#/components/responses/WriteProblem410'
        '422':
          $ref: '#/components/responses/WriteProblem422'
        '429':
          $ref: '#/components/responses/WriteProblem429'
        '500':
          $ref: '#/components/responses/WriteProblem500'
        '502':
          $ref: '#/components/responses/WriteProblem502'
        '503':
          $ref: '#/components/responses/WriteProblem503'
      x-codeSamples:
        - lang: bash
          label: cURL
          source: >-
            curl -X PUT
            "https://api.alura.io/v1/workspace/listings/1834720561/inventory" \
              -H "Authorization: Bearer $ALURA_API_KEY" \
              -H "Content-Type: application/json" \
              -H "Idempotency-Key: 5f0c8e2a-4b1d-4c3e-9a7f-2b5d6e8f0a1c" \
              -d '{"products":[{"sku":"MUG-NAME-11","property_values":[{"property_id":"200","property_name":"Primary color","values":["White"],"value_ids":["6301"]}],"offerings":[{"price":"18.50","quantity":20,"is_enabled":true,"processing_profile_id":"4601"}]},{"sku":"MUG-NAME-11-BLK","property_values":[{"property_id":"200","property_name":"Primary color","values":["Black"],"value_ids":["6302"]}],"offerings":[{"price":"21.00","quantity":15,"is_enabled":true,"processing_profile_id":"4601"}]}],"price_on_property":["200"],"quantity_on_property":["200"],"sku_on_property":["200"]}'
        - lang: typescript
          label: TypeScript
          source: >-
            const res = await
            fetch('https://api.alura.io/v1/workspace/listings/1834720561/inventory',
            {
              method: 'PUT',
              headers: {
                Authorization: `Bearer ${process.env.ALURA_API_KEY}`,
                'Content-Type': 'application/json',
                'Idempotency-Key': '5f0c8e2a-4b1d-4c3e-9a7f-2b5d6e8f0a1c',
              },
              body: JSON.stringify({
                "products": [
                  {
                    "sku": "MUG-NAME-11",
                    "property_values": [
                      {
                        "property_id": "200",
                        "property_name": "Primary color",
                        "values": [
                          "White"
                        ],
                        "value_ids": [
                          "6301"
                        ]
                      }
                    ],
                    "offerings": [
                      {
                        "price": "18.50",
                        "quantity": 20,
                        "is_enabled": true,
                        "processing_profile_id": "4601"
                      }
                    ]
                  },
                  {
                    "sku": "MUG-NAME-11-BLK",
                    "property_values": [
                      {
                        "property_id": "200",
                        "property_name": "Primary color",
                        "values": [
                          "Black"
                        ],
                        "value_ids": [
                          "6302"
                        ]
                      }
                    ],
                    "offerings": [
                      {
                        "price": "21.00",
                        "quantity": 15,
                        "is_enabled": true,
                        "processing_profile_id": "4601"
                      }
                    ]
                  }
                ],
                "price_on_property": [
                  "200"
                ],
                "quantity_on_property": [
                  "200"
                ],
                "sku_on_property": [
                  "200"
                ]
              }),
            });

            console.log(await res.json());
        - lang: python
          label: Python
          source: |-
            import json
            import os
            import urllib.request

            request = urllib.request.Request(
                "https://api.alura.io/v1/workspace/listings/1834720561/inventory",
                method="PUT",
                data=json.dumps({
                  "products": [
                    {
                      "sku": "MUG-NAME-11",
                      "property_values": [
                        {
                          "property_id": "200",
                          "property_name": "Primary color",
                          "values": [
                            "White"
                          ],
                          "value_ids": [
                            "6301"
                          ]
                        }
                      ],
                      "offerings": [
                        {
                          "price": "18.50",
                          "quantity": 20,
                          "is_enabled": true,
                          "processing_profile_id": "4601"
                        }
                      ]
                    },
                    {
                      "sku": "MUG-NAME-11-BLK",
                      "property_values": [
                        {
                          "property_id": "200",
                          "property_name": "Primary color",
                          "values": [
                            "Black"
                          ],
                          "value_ids": [
                            "6302"
                          ]
                        }
                      ],
                      "offerings": [
                        {
                          "price": "21.00",
                          "quantity": 15,
                          "is_enabled": true,
                          "processing_profile_id": "4601"
                        }
                      ]
                    }
                  ],
                  "price_on_property": [
                    "200"
                  ],
                  "quantity_on_property": [
                    "200"
                  ],
                  "sku_on_property": [
                    "200"
                  ]
                }).encode(),
                headers={
                    "Authorization": f"Bearer {os.environ['ALURA_API_KEY']}",
                    "Content-Type": "application/json",
                    "Idempotency-Key": "5f0c8e2a-4b1d-4c3e-9a7f-2b5d6e8f0a1c",
                },
            )
            with urllib.request.urlopen(request) as response:
                print(json.load(response))
components:
  headers:
    Request-Id:
      description: '`req_` + ULID; quote it when reporting a problem.'
      schema:
        type: string
    Alura-Credits-Cost:
      description: API credits this call cost.
      schema:
        type: integer
    Alura-Credits-Remaining:
      description: >-
        API credits left in the workspace's monthly allowance, counting calls
        still in flight. Absent when it cannot be read right now.
      schema:
        type: integer
  responses:
    WriteProblem400:
      description: >-
        Error. A refusal of a write Alura recorded carries its `change_id`, and
        by code `budget`, `reason`, `changed`, `missing`, `reconnect_url` or
        `missing_scopes`.
      content:
        application/problem+json:
          schema:
            $ref: '#/components/schemas/WriteProblem'
    Problem401:
      description: Error
      content:
        application/problem+json:
          schema:
            $ref: '#/components/schemas/Problem'
          example:
            type: https://docs.alura.io/errors/unauthorized
            title: Unauthorized
            status: 401
            code: unauthorized
            detail: Unauthorized
            suggestion: 'Send a valid API key as `Authorization: Bearer alura_sk_...`.'
            retryable: false
            request_id: req_01JQ5W3H8M2N4P6R8T0V2X4Z6B
    WriteProblem402:
      description: >-
        Error. A refusal of a write Alura recorded carries its `change_id`, and
        by code `budget`, `reason`, `changed`, `missing`, `reconnect_url` or
        `missing_scopes`.
      content:
        application/problem+json:
          schema:
            $ref: '#/components/schemas/WriteProblem'
    WriteProblem403:
      description: >-
        Error. A refusal of a write Alura recorded carries its `change_id`, and
        by code `budget`, `reason`, `changed`, `missing`, `reconnect_url` or
        `missing_scopes`.
      content:
        application/problem+json:
          schema:
            $ref: '#/components/schemas/WriteProblem'
    WriteProblem404:
      description: >-
        Error. A refusal of a write Alura recorded carries its `change_id`, and
        by code `budget`, `reason`, `changed`, `missing`, `reconnect_url` or
        `missing_scopes`.
      content:
        application/problem+json:
          schema:
            $ref: '#/components/schemas/WriteProblem'
    Problem405:
      description: Error
      content:
        application/problem+json:
          schema:
            $ref: '#/components/schemas/Problem'
          example:
            type: https://docs.alura.io/errors/method_not_allowed
            title: Method not allowed
            status: 405
            code: method_not_allowed
            detail: Method not allowed
            suggestion: Use one of the methods in the Allow header.
            retryable: false
            request_id: req_01JQ5W3H8M2N4P6R8T0V2X4Z6B
    WriteProblem409:
      description: >-
        Error. A refusal of a write Alura recorded carries its `change_id`, and
        by code `budget`, `reason`, `changed`, `missing`, `reconnect_url` or
        `missing_scopes`.
      content:
        application/problem+json:
          schema:
            $ref: '#/components/schemas/WriteProblem'
    WriteProblem410:
      description: >-
        Error. A refusal of a write Alura recorded carries its `change_id`, and
        by code `budget`, `reason`, `changed`, `missing`, `reconnect_url` or
        `missing_scopes`.
      content:
        application/problem+json:
          schema:
            $ref: '#/components/schemas/WriteProblem'
    WriteProblem422:
      description: >-
        Error. A refusal of a write Alura recorded carries its `change_id`, and
        by code `budget`, `reason`, `changed`, `missing`, `reconnect_url` or
        `missing_scopes`.
      content:
        application/problem+json:
          schema:
            $ref: '#/components/schemas/WriteProblem'
    WriteProblem429:
      description: >-
        Error. A refusal of a write Alura recorded carries its `change_id`, and
        by code `budget`, `reason`, `changed`, `missing`, `reconnect_url` or
        `missing_scopes`.
      content:
        application/problem+json:
          schema:
            $ref: '#/components/schemas/WriteProblem'
    WriteProblem500:
      description: >-
        Error. A refusal of a write Alura recorded carries its `change_id`, and
        by code `budget`, `reason`, `changed`, `missing`, `reconnect_url` or
        `missing_scopes`.
      content:
        application/problem+json:
          schema:
            $ref: '#/components/schemas/WriteProblem'
    WriteProblem502:
      description: >-
        Error. A refusal of a write Alura recorded carries its `change_id`, and
        by code `budget`, `reason`, `changed`, `missing`, `reconnect_url` or
        `missing_scopes`.
      content:
        application/problem+json:
          schema:
            $ref: '#/components/schemas/WriteProblem'
    WriteProblem503:
      description: >-
        Error. A refusal of a write Alura recorded carries its `change_id`, and
        by code `budget`, `reason`, `changed`, `missing`, `reconnect_url` or
        `missing_scopes`.
      content:
        application/problem+json:
          schema:
            $ref: '#/components/schemas/WriteProblem'
  schemas:
    WriteProblem:
      type: object
      description: >-
        RFC 9457 problem details. A refusal of a write Alura recorded carries
        its `change_id`, and by code `budget`, `reason`, `changed`, `missing`,
        `reconnect_url` or `missing_scopes`.
      properties:
        type:
          type: string
          format: uri
        title:
          type: string
        status:
          type: integer
        code:
          type: string
          description: A code from the error catalog; new codes may be added.
          x-extensible-enum:
            - invalid_request
            - unknown_parameter
            - invalid_cursor
            - cursor_window_exceeded
            - invalid_reference
            - id_type_mismatch
            - invalid_keyword
            - shop_id_required
            - listing_not_publishable
            - sales_window_not_covered
            - unauthorized
            - credits_exhausted
            - plan_required
            - insufficient_scope
            - workspace_required
            - workspace_locked
            - your_shop_unavailable
            - writes_suspended
            - browser_refused
            - role_required
            - impersonation_refused
            - recent_sign_in_required
            - etsy_scope_required
            - etsy_partner_required
            - not_found
            - not_collected
            - not_found_on_etsy
            - shop_opted_out
            - method_not_allowed
            - conflict
            - key_limit_reached
            - reconnect_required
            - settings_not_fetched
            - listing_busy
            - settings_busy
            - shop_create_busy
            - idempotency_partial_unverifiable
            - listing_has_variations
            - changed_since
            - change_not_revertable
            - listing_in_ab_test
            - activation_skipped
            - idempotency_processing
            - confirmation_required
            - test_shop_active_cap
            - write_outcome_unknown
            - unprocessable
            - listing_removed_on_etsy
            - endpoint_removed
            - rate_limited
            - throttled
            - daily_credit_cap_exceeded
            - credits_reserved
            - fetch_limit_reached
            - write_rate_limited
            - sync_cooldown
            - shop_write_budget_exhausted
            - internal_error
            - write_misconfigured
            - upstream_unavailable
            - credits_unavailable
            - service_unavailable
            - fetch_unavailable
            - create_lock_unavailable
            - writes_paused
            - etsy_capacity
            - upstream_timeout
        detail:
          type: string
        suggestion:
          type: string
        retryable:
          type: boolean
        request_id:
          type: string
        upgrade_url:
          type: string
          format: uri
          description: 'credits_exhausted and plan_required: where to upgrade the plan.'
        credits_needed:
          type: integer
          description: 'API credit refusals: what the call needed.'
        credits_remaining:
          type: integer
          description: >-
            API credit refusals: what is left (of the month, or of the day for
            daily_credit_cap_exceeded).
        resets_at:
          type: string
          format: date-time
          description: >-
            credits_exhausted and daily_credit_cap_exceeded: when the limit
            resets.
        change_id:
          type: string
          description: >-
            The recorded write this refusal answers, as its change (`chn_...`):
            read it (`GET /v1/workspace/changes/{id}`) before writing again.
        budget:
          type: string
          description: >-
            `shop_write_budget_exhausted`: which of the shop's Etsy write
            budgets ran out (`creates`, `activations`, `etsy_calls`).
        reason:
          description: >-
            Why, as an identifier: for `change_not_revertable`, why the revert
            was refused; null when none was named.
          type:
            - string
            - 'null'
        changed:
          anyOf:
            - type: array
              items:
                type: string
            - type: 'null'
          description: >-
            `changed_since`: the fields that changed on Etsy since the change;
            null when none was named.
        missing:
          anyOf:
            - type: array
              items:
                type: string
            - type: 'null'
          description: >-
            `listing_not_publishable`: what Etsy said the listing lacks to
            publish; null when it named none.
        reconnect_url:
          type: string
          description: >-
            `reconnect_required` and `etsy_scope_required`: where the shop is
            reconnected in Alura.
        missing_scopes:
          anyOf:
            - type: array
              items:
                type: string
            - type: 'null'
          description: >-
            `etsy_scope_required`: the Etsy scopes the shop's connection lacks;
            null when none was named.
      required:
        - type
        - title
        - status
        - code
        - detail
        - suggestion
        - retryable
        - request_id
    Problem:
      type: object
      description: RFC 9457 problem details.
      properties:
        type:
          type: string
          format: uri
        title:
          type: string
        status:
          type: integer
        code:
          type: string
          description: A code from the error catalog; new codes may be added.
          x-extensible-enum:
            - invalid_request
            - unknown_parameter
            - invalid_cursor
            - cursor_window_exceeded
            - invalid_reference
            - id_type_mismatch
            - invalid_keyword
            - shop_id_required
            - listing_not_publishable
            - sales_window_not_covered
            - unauthorized
            - credits_exhausted
            - plan_required
            - insufficient_scope
            - workspace_required
            - workspace_locked
            - your_shop_unavailable
            - writes_suspended
            - browser_refused
            - role_required
            - impersonation_refused
            - recent_sign_in_required
            - etsy_scope_required
            - etsy_partner_required
            - not_found
            - not_collected
            - not_found_on_etsy
            - shop_opted_out
            - method_not_allowed
            - conflict
            - key_limit_reached
            - reconnect_required
            - settings_not_fetched
            - listing_busy
            - settings_busy
            - shop_create_busy
            - idempotency_partial_unverifiable
            - listing_has_variations
            - changed_since
            - change_not_revertable
            - listing_in_ab_test
            - activation_skipped
            - idempotency_processing
            - confirmation_required
            - test_shop_active_cap
            - write_outcome_unknown
            - unprocessable
            - listing_removed_on_etsy
            - endpoint_removed
            - rate_limited
            - throttled
            - daily_credit_cap_exceeded
            - credits_reserved
            - fetch_limit_reached
            - write_rate_limited
            - sync_cooldown
            - shop_write_budget_exhausted
            - internal_error
            - write_misconfigured
            - upstream_unavailable
            - credits_unavailable
            - service_unavailable
            - fetch_unavailable
            - create_lock_unavailable
            - writes_paused
            - etsy_capacity
            - upstream_timeout
        detail:
          type: string
        suggestion:
          type: string
        retryable:
          type: boolean
        request_id:
          type: string
        upgrade_url:
          type: string
          format: uri
          description: 'credits_exhausted and plan_required: where to upgrade the plan.'
        credits_needed:
          type: integer
          description: 'API credit refusals: what the call needed.'
        credits_remaining:
          type: integer
          description: >-
            API credit refusals: what is left (of the month, or of the day for
            daily_credit_cap_exceeded).
        resets_at:
          type: string
          format: date-time
          description: >-
            credits_exhausted and daily_credit_cap_exceeded: when the limit
            resets.
      required:
        - type
        - title
        - status
        - code
        - detail
        - suggestion
        - retryable
        - request_id
  securitySchemes:
    apiKey:
      type: http
      scheme: bearer
      description: 'An API key: `Authorization: Bearer alura_sk_...`.'

````

This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.