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

# Reorder resolution rules

> Atomically update ``order_index`` on a contiguous block of rules in a single transaction. Every rule referenced by ``short_id`` must belong to the caller's organization, otherwise the whole call aborts with ``404`` and no rules are mutated. Returns ``403`` when the caller can see the organization but lacks CHANGE permission (a read-only key). Returns the affected rules in their new evaluation order.



## OpenAPI

````yaml /openapi/openapi-resolver.json post /resolver/api/v1/resolution-rules/reorder
openapi: 3.1.0
info:
  title: Resolver API
  version: 1.0.0
  description: >
    GS1 Digital Link resolution with content negotiation and linkset support.


    ## Authentication


    All endpoints require an API key passed via the `X-API-Key` HTTP header,
    unless otherwise noted.


    ```

    X-API-Key: csb_<body>_<checksum>

    ```


    Generate API keys in **Settings > API Keys** in your dashboard, or via the
    Account API.

    Session-based (cookie) authentication is also accepted for browser-based
    access.


    ## Rate Limits


    | Tier        | Requests / minute | Requests / day |

    |-------------|-------------------|----------------|

    | Default     | 300               | 10,000         |

    | Custom      | Contact us        | Contact us     |


    Those windows are per key. Your plan also caps each organization per hour,
    across every key,

    login and session acting for it: 100 requests on Free (or while a
    subscription is lapsed),

    10,000 on Business. While a subscription is lapsed, any method other than
    `GET`, `HEAD` and

    `OPTIONS` returns `403`.


    Rate-limit headers are included on every response so callers can
    self-throttle without

    hitting our 429s ("informed governor"):


    - `RateLimit-Policy` — every active window, e.g. `300;w=60, 10000;w=86400`

    - `RateLimit-Limit` — quota for the **most-restrictive** currently-active
    window

    - `RateLimit-Remaining` — requests left in that window

    - `RateLimit-Reset` — seconds until that window resets (relative; clock-skew
    safe)


    Legacy `X-RateLimit-*` aliases are also emitted for back-compat.
    `X-RateLimit-Reset`

    keeps the absolute Unix-timestamp shape to avoid breaking existing
    consumers.


    When rate-limited, you receive `429 Too Many Requests` with a
    `retry_after_seconds` field

    in the error envelope and a `Retry-After` header.


    ## Pagination


    List endpoints return paginated results in this envelope:


    ```json

    {
      "data": [...],
      "pagination": {
        "page": 1,
        "page_size": 25,
        "total_count": 342,
        "total_pages": 14,
        "has_next": true,
        "has_previous": false
      }
    }

    ```


    Use `?page=2&page_size=50` query parameters. Maximum page size is 100.


    ## Error Responses


    All errors conform to [RFC 9457 Problem
    Details](https://www.rfc-editor.org/rfc/rfc9457)

    with `Content-Type: application/problem+json`:


    ```json

    {
      "type": "https://closient.com/docs/errors/not_found",
      "title": "Not Found",
      "status": 404,
      "detail": "The requested resource was not found.",
      "error_code": "not_found",
      "retryable": false,
      "timestamp": "2026-03-31T12:00:00+00:00"
    }

    ```


    Common error codes: `unauthorized` (401), `forbidden` (403), `not_found`
    (404),

    `validation_error` (422), `rate_limited` (429), `internal_error` (500).
  termsOfService: https://www.closient.com/terms/
servers:
  - url: https://www.closient.com
security: []
tags:
  - name: Resolver
    description: GS1 Digital Link resolution with content negotiation and linkset support.
  - name: Custom URLs
    description: >-
      Reusable custom-URL catalog — create, list, edit, and delete the custom
      redirect destinations that resolution rules point at.
  - name: Resolver Configuration
    description: >-
      Organization resolver settings and per-product resolver state — the
      routing timezone, whether the resolver serves a product, and its per-GTIN
      behavior controls (enhanced resolution, expiry, serial policy, shelf-life
      offset, age gate). The same audited writes the dashboard pages make.
  - name: Link-type sections
    description: >-
      Organization-owned GS1 link-type records — documents (GDTI), coupons (GCN)
      and service relations (GSRN): list, read, create, update and delete. The
      same audited writes the dashboard's Link-type sections page makes.
  - name: Link-type documents
    description: The barcode for one stored GS1 document (GDTI, GS1 AI 253).
  - name: Link-type coupons
    description: >-
      The barcode for one stored GS1 coupon (GCN, GS1 AI 255; not a Stripe
      coupon).
  - name: Link-type service relations
    description: >-
      The barcode for one stored GS1 service relation (GSRN, GS1 AI 8017 or
      8018).
  - name: Lot groups
    description: >-
      Lot groups — named, brand-owned sets of lots that a rule can be scoped to:
      list, read, create, list members, add members and remove a member. Groups
      are never renamed or deleted. The same audited writes the dashboard's lot
      group pages make.
  - name: Serial groups
    description: >-
      Serial groups — named, brand-owned sets of serials that a rule can be
      scoped to: list, read, create, list members, add members and remove a
      member. Groups are never renamed or deleted. The same audited writes the
      dashboard's serial group pages make.
  - name: Routing rules
    description: >-
      Conditional routing rules — per-product rules that decorate the redirect a
      scan resolves to (query parameters and/or the path) when the scanned date,
      lot or serial matches: list, read, create, update, activate and
      deactivate. Rules are never deleted. The same audited writes the
      dashboard's Routing rules pages make.
  - name: Verification
    description: >-
      Serial verification (`gs1:verificationService`) — tiered, rate-limited
      responses for serialized GTIN scans. Experimental v1; see the
      verification-service guide.
  - name: GS1 Primitives (Public)
    description: >-
      Keyless GS1 Digital Link primitives — parse, validate, build, decompress,
      and check-digit analysis. **No API key, no signup.** Pure functions over
      strings: no database, no network, no catalog data. IP-throttled and
      edge-cached so repeat calls cost nothing. This is the reference
      implementation the resolver itself runs on.
  - name: Resolver Custom Hostnames
    description: >-
      BYO domain — register a customer-owned hostname, publish the CNAME
      records, verify ownership, and serve an org's Digital Link QRs from its
      own DNS.
externalDocs:
  description: Closient Documentation
  url: https://docs.closient.com
paths:
  /resolver/api/v1/resolution-rules/reorder:
    post:
      tags:
        - Resolver
      summary: Reorder resolution rules
      description: >-
        Atomically update ``order_index`` on a contiguous block of rules in a
        single transaction. Every rule referenced by ``short_id`` must belong to
        the caller's organization, otherwise the whole call aborts with ``404``
        and no rules are mutated. Returns ``403`` when the caller can see the
        organization but lacks CHANGE permission (a read-only key). Returns the
        affected rules in their new evaluation order.
      operationId: reorder_resolution_rules
      parameters:
        - in: query
          name: organization_id
          schema:
            description: >-
              Organization to act on. Omit it: an API key acts on its own
              organization, and a session or OAuth caller on its single
              organization. Required only for a session or OAuth caller that
              belongs to more than one organization (400 without it).
            title: Organization Id
            format: shortuuid
            maxLength: 22
            minLength: 22
            pattern: ^[23456789ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnopqrstuvwxyz]{22}$
            type: string
          required: false
          description: >-
            Organization to act on. Omit it: an API key acts on its own
            organization, and a session or OAuth caller on its single
            organization. Required only for a session or OAuth caller that
            belongs to more than one organization (400 without it).
      requestBody:
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/ReorderInput'
        required: true
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema:
                items:
                  $ref: '#/components/schemas/ResolutionRuleOut'
                title: Response
                type: array
        '400':
          description: Bad Request
          content:
            application/problem+json:
              schema:
                $ref: '#/components/schemas/ErrorOut'
        '401':
          description: Unauthorized
          content:
            application/problem+json:
              schema:
                $ref: '#/components/schemas/ErrorOut'
        '403':
          description: Forbidden
          content:
            application/problem+json:
              schema:
                $ref: '#/components/schemas/ErrorOut'
        '404':
          description: Not Found
          content:
            application/problem+json:
              schema:
                $ref: '#/components/schemas/ErrorOut'
        '405':
          description: Method Not Allowed
          content:
            application/problem+json:
              schema:
                $ref: '#/components/schemas/ErrorOut'
        '422':
          description: Unprocessable Content
          content:
            application/problem+json:
              schema:
                $ref: '#/components/schemas/ErrorOut'
        '429':
          description: Too Many Requests
          content:
            application/problem+json:
              schema:
                $ref: '#/components/schemas/ErrorOut'
      security:
        - APIKeyHeaderAuth: []
        - OAuthTokenAuth: []
        - CookieGatedSessionAuth: []
components:
  schemas:
    ReorderInput:
      description: >-
        Body for the bulk reorder endpoint — the list of new ``(rule,
        order_index)`` pairs.
      examples:
        - rules:
            - id: keATfB8VP2gSjcnTbsMNQL
              order_index: 1
            - id: xYzAbCdEfGhIjKlMnOpQrS
              order_index: 2
      properties:
        rules:
          description: >-
            Complete new ordering for a contiguous block of rules. The API
            applies the changes in a single transaction; any short_id in the
            list that doesn't belong to the caller's organization aborts the
            whole reorder with ``404`` and no rules are mutated.
          items:
            $ref: '#/components/schemas/ReorderItem'
          title: Rules
          type: array
      required:
        - rules
      title: ReorderInput
      type: object
    ResolutionRuleOut:
      description: >-
        A resolution rule as read from the API.


        Returned by ``GET /resolution-rules/{id}`` and the list/reorder

        endpoints. Mirrors ``ResolutionRule``.


        ``scope_id`` is the canonical text form of the rule's scope (a product,

        brand or lot identifier). Its format is stable, so consumers are not
        made

        to migrate when the way scopes are stored changes.
      examples:
        - annual_end_mmdd: 01-05
          annual_start_mmdd: 11-15
          created: '2025-10-01T09:00:00Z'
          custom_url: https://acmesnacks.com/holiday-promo
          destination_type: CUSTOM_URL
          enabled: true
          metadata:
            order_id: '6735'
          modified: '2025-10-15T14:30:00Z'
          on_custom_url_dead: SKIP_RULE
          order_index: 1
          organization_id: b2c3d4e5-f678-9012-abcd-ef2345678901
          product_id: a1b2c3d4-e5f6-7890-abcd-ef1234567890
          scope_id: '00012345678905'
          scope_type: PRODUCT
          timezone: America/New_York
      properties:
        metadata:
          additionalProperties:
            maxLength: 500
            type: string
          description: >-
            Developer-attached key/value data attached to this object. Up to 50
            keys; key max 40 chars, value max 500 chars.
          maxProperties: 50
          propertyNames:
            maxLength: 40
          title: Metadata
          type: object
        id:
          description: >-
            URL-safe 22-character shortuuid encoding of the row's UUID primary
            key. Stable across the row's lifetime; suitable for sharing in URLs,
            log lines, and external SDK clients. Accepted on input as either the
            shortuuid form or the canonical UUID form
            (``xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx``).
          format: shortuuid
          maxLength: 22
          minLength: 22
          pattern: ^[23456789ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnopqrstuvwxyz]{22}$
          title: Id
          type: string
        system:
          default: false
          description: >-
            Whether this is the implicit, system-managed default rule rather
            than a user-created one. Always ``false`` for rules returned by the
            list/CRUD endpoints — those are all user-managed DB rows. The
            default rule (the baseline hosted-page fallback applied when no
            other rule matches) is served separately by ``GET
            .../resolution-rules/default`` with ``system`` set to ``true``; it
            cannot be created, edited, deleted, or reordered.
          title: System
          type: boolean
        scope_type:
          $ref: '#/components/schemas/ScopeTypeEnum'
          description: >-
            Hierarchy level at which this rule applies. Mirrors ``ScopeType``.
            Specificity ascends ``ORGANIZATION → BRAND → PRODUCT → BATCH →
            SERIAL`` — the evaluator walks scopes most-specific first, so a rule
            scoped to a single serial beats a rule scoped to the whole brand.
        scope_id:
          anyOf:
            - type: string
            - type: 'null'
          description: >-
            Identifier of the scoped entity. **Required when ``scope_type !=
            'ORGANIZATION'``** (organization-wide rules use the caller's
            organization). Which entity it names depends on ``scope_type``: the
            brand for ``BRAND``, the product for ``PRODUCT``, the lot/serial for
            ``BATCH``/``SERIAL``, the group for ``LOT_GROUP``/``SERIAL_GROUP``.
            Accepted in either the 22-character short id or the canonical
            36-character UUID form; responses always return the short id. The
            entity must exist and belong to the calling organization -- an id
            that names nothing is rejected with a 422 rather than stored.
            Internally the scope is a typed foreign key, not this string;
            ``scope_id`` remains the request/response field so consumers are not
            asked to migrate for a storage change.
          title: Scope Id
        order_index:
          description: >-
            Evaluation order within the rule's ``(scope_type, scope_id)``
            bucket. Lower values are evaluated first; the first matching rule
            wins. Unique per ``(scope_type, scope_id, order_index)`` —
            duplicates are rejected by a per-scope unique index in the database.
          title: Order Index
          type: integer
        enabled:
          description: >-
            Whether the rule is currently active. Disabled rules are skipped by
            the evaluator but kept in the listing for easy re-enable.
          title: Enabled
          type: boolean
        organization_id:
          anyOf:
            - description: >-
                URL-safe 22-character shortuuid encoding of the row's UUID
                primary key. Stable across the row's lifetime; suitable for
                sharing in URLs, log lines, and external SDK clients. Accepted
                on input as either the shortuuid form or the canonical UUID form
                (``xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx``).
              format: shortuuid
              maxLength: 22
              minLength: 22
              pattern: >-
                ^[23456789ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnopqrstuvwxyz]{22}$
              type: string
            - type: 'null'
          description: >-
            UUID of the organization that owns this rule. Always populated for
            API-managed rules (the create endpoint takes the organization from
            the caller); ``null`` only for legacy/system-seeded rules.
          title: Organization Id
        product_id:
          anyOf:
            - description: >-
                URL-safe 22-character shortuuid encoding of the row's UUID
                primary key. Stable across the row's lifetime; suitable for
                sharing in URLs, log lines, and external SDK clients. Accepted
                on input as either the shortuuid form or the canonical UUID form
                (``xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx``).
              format: shortuuid
              maxLength: 22
              minLength: 22
              pattern: >-
                ^[23456789ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnopqrstuvwxyz]{22}$
              type: string
            - type: 'null'
          description: >-
            UUID of the product the rule is bound to. For a ``PRODUCT``-scoped
            rule this is the scope itself and is always populated (it is
            resolved from ``scope_id`` on write); ``null`` at every other scope.
            When provided on write it must name a product **this organization
            owns** — a product belonging to another organization, or one no
            organization has claimed, is rejected with a ``404`` that is
            indistinguishable from a product that does not exist.
          title: Product Id
        absolute_start_at:
          anyOf:
            - format: date-time
              type: string
            - type: 'null'
          description: >-
            Inclusive lower bound of the rule's active window — the rule matches
            when ``now() >= absolute_start_at``. ``null`` means no lower bound.
            Compared in the rule's ``timezone``.
          title: Absolute Start At
        absolute_end_at:
          anyOf:
            - format: date-time
              type: string
            - type: 'null'
          description: >-
            Exclusive upper bound of the rule's active window — the rule matches
            when ``now() < absolute_end_at``. ``null`` means no upper bound.
            Compared in the rule's ``timezone``.
          title: Absolute End At
        annual_start_mmdd:
          anyOf:
            - maxLength: 5
              pattern: ^(0[1-9]|1[0-2])-(0[1-9]|[12]\d|3[01])$
              type: string
            - type: 'null'
          description: >-
            Annually-recurring start date in ``MM-DD`` format (e.g. ``11-15``).
            When ``annual_start_mmdd`` is later in the year than
            ``annual_end_mmdd`` the window wraps year-end (e.g. ``11-15`` →
            ``01-05`` is mid-November to early January). ``null`` means no
            annual constraint.
          title: Annual Start Mmdd
        annual_end_mmdd:
          anyOf:
            - maxLength: 5
              pattern: ^(0[1-9]|1[0-2])-(0[1-9]|[12]\d|3[01])$
              type: string
            - type: 'null'
          description: >-
            Annually-recurring end date in ``MM-DD`` format (e.g. ``01-05``).
            See ``annual_start_mmdd`` for wrap-around semantics. ``null`` means
            no annual constraint. Both ends should be set together; setting only
            one is accepted by the API but ignored by the evaluator.
          title: Annual End Mmdd
        days_of_week:
          anyOf:
            - items:
                $ref: '#/components/schemas/WeekdayEnum'
              type: array
            - type: 'null'
          description: >-
            Days the rule may match, using Python's ``datetime.weekday()``
            convention: ``0`` = Monday, ``6`` = Sunday. Duplicates are
            deduplicated and the result is sorted ascending. ``null`` (or empty
            list) means every day matches. Evaluated in the rule's ``timezone``.
          title: Days Of Week
        time_of_day_start:
          anyOf:
            - format: time
              type: string
            - type: 'null'
          description: >-
            Inclusive lower bound on time-of-day, ``HH:MM`` 24-hour. Rule
            matches when ``current_time >= time_of_day_start`` in the rule's
            ``timezone``. When start is later than end the window wraps midnight
            (e.g. ``22:00`` → ``02:00`` is the late-night window). ``null``
            means no lower bound.
          title: Time Of Day Start
        time_of_day_end:
          anyOf:
            - format: time
              type: string
            - type: 'null'
          description: >-
            Exclusive upper bound on time-of-day, ``HH:MM`` 24-hour. Rule
            matches when ``current_time < time_of_day_end`` in the rule's
            ``timezone``. See ``time_of_day_start`` for wrap-around semantics.
            ``null`` means no upper bound.
          title: Time Of Day End
        timezone:
          anyOf:
            - maxLength: 50
              type: string
            - type: 'null'
          description: >-
            IANA timezone name used to evaluate every other time-criteria field
            (``annual_*``, ``days_of_week``, ``time_of_day_*``, ``absolute_*``).
            E.g. ``America/New_York``, ``Europe/Berlin``, ``UTC``. Falls back to
            the organization's ``OrganizationResolverSettings.routing_timezone``
            when ``null``.
          title: Timezone
        link_type:
          anyOf:
            - maxLength: 100
              type: string
            - type: 'null'
          description: >-
            GS1 Web Vocabulary CURIE that the rule applies to (e.g. ``gs1:pip``
            for Product Information Page, ``gs1:hasRecallInformation`` for
            recall redirects). When present the rule only matches resolutions
            for that link type; ``null`` matches all link types. See the GS1 Web
            Vocabulary for the full set of CURIEs.
          title: Link Type
        location_countries:
          anyOf:
            - items:
                type: string
              type: array
            - type: 'null'
          description: >-
            Allow list of ISO 3166-1 alpha-2 country codes the rule applies to.
            Matched against the IP-derived country of the scan request. `null`
            or empty list = any country. Case-insensitive.
          title: Location Countries
        location_regions:
          anyOf:
            - items:
                type: string
              type: array
            - type: 'null'
          description: >-
            Allow list of subdivision (state / province / region) names the rule
            applies to. Matched against the IP-derived region name of the scan
            request. `null` or empty list = any region. Case-insensitive.
          title: Location Regions
        location_cities:
          anyOf:
            - items:
                type: string
              type: array
            - type: 'null'
          description: >-
            Allow list of city names the rule applies to. Matched against the
            IP-derived city name of the scan request. `null` or empty list = any
            city. Case-insensitive.
          title: Location Cities
        destination_type:
          $ref: '#/components/schemas/DestinationTypeEnum'
          description: >-
            Where to send the resolution. ``HOSTED_PAGE`` renders the Closient
            product page; ``CUSTOM_URL`` 302s to ``custom_url``.
        custom_url:
          anyOf:
            - maxLength: 2048
              type: string
            - type: 'null'
          description: >-
            External URL to redirect to. **Required when ``destination_type ==
            'CUSTOM_URL'``** (enforced both at the schema level and by a
            database CHECK constraint). Maximum 2048 characters. On write the
            URL is stored as a reusable custom-URL catalog entry for the
            organization (deduped by URL); on read it reflects that catalog
            entry. Health is monitored out-of-band; see ``on_custom_url_dead``
            for failure behavior.
          title: Custom Url
        on_custom_url_dead:
          $ref: '#/components/schemas/FailurePolicyEnum'
          description: >-
            Behavior when the URL-health monitor has marked ``custom_url`` dead.
            ``SKIP_RULE`` falls through to the next matching rule;
            ``FALLBACK_TO_HOSTED`` short-circuits to the Closient-hosted product
            page. Live URLs are followed regardless of this setting.
        section_anchor:
          anyOf:
            - enum:
                - accessories
                - activityIdeas
                - alerts
                - apps
                - backgroundInfo
                - brand-links
                - brandHomepageClinical
                - brandHomepagePatient
                - careersInfo
                - certifications
                - claims
                - consumables
                - date-countdown
                - dscsa-drug-id
                - dscsa-recall-status
                - dscsa-safety
                - dscsa-traceability
                - epcis
                - epil
                - eventsInfo
                - expiry-notice
                - faq
                - firmware
                - gallery
                - homepage
                - ingredients
                - instructions
                - itip-piece
                - jws
                - leaveReview
                - locationInfo
                - logisticsInfo
                - loyaltyProgram
                - manual
                - masterData
                - menuInfo
                - nutrition
                - openingHoursInfo
                - parts
                - paymentLink
                - product-info
                - production-location
                - promotion
                - quick-facts
                - recipes
                - recycling
                - register-product
                - registryEntry
                - reportFound
                - retailer-badges
                - review
                - safety-notices
                - scheduleTime
                - sensitivities
                - smpc
                - socials
                - state-notices
                - statisticInfo
                - subscribe
                - traceability
                - unverified-unit
                - userAgreement
                - verificationService
                - warranty
                - whatsInTheBox
                - where-to-buy
              type: string
            - type: 'null'
          description: >-
            Optional section anchor that deep-links a hosted-page scan to a
            specific kebab-case section of the product page (e.g.
            `where-to-buy`, `ingredients`, `dscsa-recall-status`), or to one
            specific brand CTA link within the `brand-links` section, addressed
            by its bare camelCase GS1 link-type short name (e.g. `review`,
            `leaveReview`, `promotion`). When set on a `HOSTED_PAGE` rule the
            resolver appends `#anchor` to the redirect URL so the browser
            scrolls directly to that section or link. Must be `null` whenever
            `destination_type != 'HOSTED_PAGE'` — for `CUSTOM_URL` rules, embed
            any anchor directly in `custom_url`. The frontend resolver-config
            picker is responsible for enumerating the anchors available on the
            resolved product; canonical section anchors and per-link anchors are
            the section and link-type short names of the product.
          format: resolver-section-anchor
          title: Section Anchor
        created:
          description: Server-side ISO 8601 timestamp of when the rule was created (UTC).
          format: date-time
          title: Created
          type: string
        modified:
          description: >-
            Server-side ISO 8601 timestamp of the rule's last modification
            (UTC).
          format: date-time
          title: Modified
          type: string
      required:
        - id
        - scope_type
        - order_index
        - enabled
        - destination_type
        - on_custom_url_dead
        - created
        - modified
      title: ResolutionRuleOut
      type: object
    ErrorOut:
      description: |-
        RFC 9457 Problem Details response.

        All API errors are returned in this format with Content-Type:
        application/problem+json.
      examples:
        - detail: The requested resource was not found.
          error_code: not_found
          retryable: false
          status: 404
          timestamp: '2026-03-31T12:00:00+00:00'
          title: Not Found
          type: https://closient.com/docs/errors/not_found
        - detail: Validation error.
          details:
            - loc:
                - body
                - name
              msg: Field required
              type: missing
          error_code: validation_error
          retryable: false
          status: 422
          timestamp: '2026-03-31T12:00:00+00:00'
          title: Validation Error
          type: https://closient.com/docs/errors/validation_error
        - detail: Rate limit exceeded. Please try again later.
          error_code: rate_limited
          retry_after: 31
          retryable: true
          status: 429
          timestamp: '2026-03-31T12:00:00+00:00'
          title: Rate Limited
          type: https://closient.com/docs/errors/rate_limited
      properties:
        type:
          description: URI reference identifying the error type.
          title: Type
          type: string
        title:
          description: Short human-readable summary of the error.
          title: Title
          type: string
        status:
          description: HTTP status code.
          title: Status
          type: integer
        detail:
          description: Human-readable explanation of this specific occurrence.
          title: Detail
          type: string
        error_code:
          description: Machine-readable error code (e.g. not_found, unauthorized).
          title: Error Code
          type: string
        retryable:
          default: false
          description: Whether retrying the same request can succeed.
          title: Retryable
          type: boolean
        timestamp:
          description: ISO 8601 timestamp of when the error occurred.
          title: Timestamp
          type: string
        retry_after:
          anyOf:
            - type: integer
            - type: 'null'
          description: Seconds to wait before retrying (when applicable).
          title: Retry After
        owner_action_required:
          anyOf:
            - type: boolean
            - type: 'null'
          description: Whether the error requires account owner intervention.
          title: Owner Action Required
        details:
          description: Additional context (validation errors, etc.).
          title: Details
      required:
        - type
        - title
        - status
        - detail
        - error_code
        - timestamp
      title: ErrorOut
      type: object
    ReorderItem:
      description: A single ``(rule, order_index)`` mapping for the bulk reorder endpoint.
      examples:
        - id: keATfB8VP2gSjcnTbsMNQL
          order_index: 1
      properties:
        id:
          description: >-
            URL-safe 22-character shortuuid encoding of the row's UUID primary
            key. Stable across the row's lifetime; suitable for sharing in URLs,
            log lines, and external SDK clients. Accepted on input as either the
            shortuuid form or the canonical UUID form
            (``xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx``).
          format: shortuuid
          maxLength: 22
          minLength: 22
          pattern: ^[23456789ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnopqrstuvwxyz]{22}$
          title: Id
          type: string
        order_index:
          description: New evaluation order — lower values evaluate first.
          title: Order Index
          type: integer
      required:
        - id
        - order_index
      title: ReorderItem
      type: object
    ScopeTypeEnum:
      description: |-
        Hierarchy level at which a resolution rule applies.

        Mirrors ``ScopeType``. Ordered from least
        specific (``ORGANIZATION``) to most specific (``SERIAL``); the
        resolver evaluator walks scopes most-specific first so a per-serial
        override beats a per-product override beats a brand-wide override.
      enum:
        - ORGANIZATION
        - BRAND
        - PRODUCT
        - BATCH
        - SERIAL
      title: ScopeTypeEnum
      type: string
    WeekdayEnum:
      description: |-
        Day-of-week value for ``ResolutionRule.days_of_week``.

        Uses the Python ``datetime.weekday()`` convention: Monday=0,
        Sunday=6. Exposed as a typed enum so the
        OpenAPI spec advertises the full valid range (``enum: [0..6]``)
        instead of the previous "any int".
      enum:
        - 0
        - 1
        - 2
        - 3
        - 4
        - 5
        - 6
      title: WeekdayEnum
      type: integer
    DestinationTypeEnum:
      enum:
        - HOSTED_PAGE
        - CUSTOM_URL
      title: DestinationTypeEnum
      type: string
    FailurePolicyEnum:
      description: |-
        What the resolver does when a rule's custom URL is unreachable.

        Mirrors ``FailurePolicy``. ``SKIP_RULE``
        falls through to the next matching rule in evaluation order;
        ``FALLBACK_TO_HOSTED`` short-circuits to the Closient-hosted product
        page. Only consulted when the URL-health monitor has marked the
        target dead — live URLs are followed regardless of policy.
      enum:
        - SKIP_RULE
        - FALLBACK_TO_HOSTED
      title: FailurePolicyEnum
      type: string
  securitySchemes:
    APIKeyHeaderAuth:
      type: apiKey
      in: header
      name: X-API-Key
    OAuthTokenAuth:
      type: http
      scheme: bearer
    CookieGatedSessionAuth:
      type: apiKey
      in: cookie
      name: sessionid

````

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