openapi: 3.1.0
info:
  title: PPM API
  version: 0.1.0-draft
  description: |
    Pricing and Promotions (PPM).

    Contract notes:
    - API Gateway base path: `/ppm`
    - Org-gated: supply `x-orgcode`.
    - Facility and channel overrides are supported where applicable.
    - Request context is captured for auditability (org/facility/channel/roles/cost-centre).
    - Auth: either `x-session-guid` (user session) or `x-api-key` (org-bound service account).
      Headers are canonical; body `session_guid`/`api_key` accepted for compatibility on POST.
    - PPM is system-of-record for price resolution, including quote pricing.
servers:
  - url: https://api.g3nretailstack.com/ppm
security:
  - sessionAuth: []
  - apiKeyAuth: []
components:
  securitySchemes:
    sessionAuth:
      type: apiKey
      in: header
      name: x-session-guid
    apiKeyAuth:
      type: apiKey
      in: header
      name: x-api-key
  parameters:
    OrgHeader:
      in: header
      name: x-orgcode
      required: true
      schema: { type: string }
    LogicalHeader:
      in: header
      name: x-logical-guid
      required: false
      schema: { type: string }
    ChannelHeader:
      in: header
      name: x-channel-code
      required: false
      schema: { type: string }
  schemas:
    BuildMeta:
      type: object
      properties:
        build_major: { type: string }
        build_minor: { type: string }
        build_id: { type: string }
      required: [build_major, build_minor, build_id]
    Stats:
      type: object
      properties:
        call: { type: string }
        service: { type: string, enum: [ppm] }
        request_id: { type: string }
        timestamp_utc: { type: string, format: date-time }
        build: { $ref: '#/components/schemas/BuildMeta' }
        actor: { type: string }
        context_source:
          type: string
          enum: [session, api_key, operator, system]
        session_fingerprint:
          type: string
          description: Non-reversible SHA-256 fingerprint of the caller session (`session_guid`) for correlation (never an auth credential).
        api_key_fingerprint:
          type: string
          description: Non-reversible SHA-256 fingerprint of the caller `api_key` for correlation (never an auth credential).
        orgcode: { type: string }
        cccode: { type: string }
        logical_guid: { type: string }
        channel_code: { type: string }
        roles:
          type: array
          items: { type: string }
      required: [call, service, timestamp_utc, build]
    Error:
      type: object
      properties:
        error_code: { type: string }
        http_status: { type: integer }
        retryable: { type: boolean }
        request_id: { type: string }
        trace_id: { type: string }
        major: { type: string }
        minor: { type: string }
        message: { type: string }
        details: { type: object }
    Envelope:
      type: object
      properties:
        success: { type: boolean }
        data: { type: object }
        error: { $ref: '#/components/schemas/Error' }
        stats: { $ref: '#/components/schemas/Stats' }
    SourceRef:
      type: object
      properties:
        kind: { type: string }
        id: { type: string }
      required: [kind, id]
    SourceRefs:
      type: array
      items: { $ref: '#/components/schemas/SourceRef' }
    IdempotencyKey:
      type: string
      description: Client-supplied idempotency key (ASCII <=128 chars). Scope is orgcode+route+idempotency_key; replay returns original response, mismatch returns 409 idempotency-conflict (retained 24h).
      maxLength: 128
    RequestContext:
      type: object
      properties:
        orgcode: { type: string }
        logical_guid: { type: string }
        channel_code: { type: string }
        cccode: { type: string }
        actor: { type: string }
        roles:
          type: array
          items: { type: string }
        context_source:
          type: string
          enum: [session, api_key, operator, system]
        session_fingerprint: { type: string }
        api_key_fingerprint: { type: string }
      required: [orgcode, actor, context_source]
      additionalProperties: false
    PolicyRefs:
      type: object
      properties:
        tax_policy_version: { type: string }
        pricing_policy_version: { type: string }
        promotion_policy_version: { type: string }
        discount_policy_version: { type: string }
        stacking_policy_version: { type: string }
        approval_policy_version: { type: string }
        tender_policy_version: { type: string }
        returns_policy_version: { type: string }
        loyalty_policy_version: { type: string }
        stored_value_policy_version: { type: string }
        earning_policy_version: { type: string }
        backorder_policy_version: { type: string }
        special_order_policy_version: { type: string }
        transfer_policy_version: { type: string }
        count_policy_version: { type: string }
        adjustment_policy_version: { type: string }
        po_policy_version: { type: string }
        matching_policy_version: { type: string }
        tolerance_policy_version: { type: string }
        receiving_policy_version: { type: string }
        qc_policy_version: { type: string }
        rtv_policy_version: { type: string }
        credit_policy_version: { type: string }
        shipping_policy_version: { type: string }
        export_policy_version: { type: string }
      additionalProperties: true
    Money:
      type: object
      properties:
        currency: { type: string }
        amount: { type: number }
      required: [currency, amount]
    UomQuantity:
      type: object
      properties:
        qty: { type: number }
        uom: { type: string }
        uom_multiplier: { type: number }
      required: [qty, uom]
    PriceScope:
      type: object
      properties:
        logical_guid: { type: string }
        channel_code: { type: string }
        customer_ref: { type: string }
        customer_tier: { type: string }
        price_level_code: { type: string }
        price_zone_code: { type: string }
        price_list_code: { type: string }
        influencer_tier: { type: string }
        employee_price: { type: boolean }
    DiscountGuardrails:
      type: object
      properties:
        max_discount_percent: { type: number }
        min_price_amount: { $ref: '#/components/schemas/Money' }
        min_price_percent_of_list: { type: number }
        max_price_amount: { $ref: '#/components/schemas/Money' }
        max_price_percent_of_list: { type: number }
        min_price_percent_of_cost: { type: number }
        allow_below_cost_percent: { type: number }
        dynamic_max_change_percent: { type: number }
        dynamic_max_change_amount: { $ref: '#/components/schemas/Money' }
        approval_thresholds:
          type: object
          properties:
            line_discount_percent: { type: number }
            line_discount_amount: { $ref: '#/components/schemas/Money' }
            order_discount_percent: { type: number }
            order_discount_amount: { $ref: '#/components/schemas/Money' }
            below_cost_percent: { type: number }
            below_cost_amount: { $ref: '#/components/schemas/Money' }
            dynamic_price_percent: { type: number }
            dynamic_price_amount: { $ref: '#/components/schemas/Money' }
    PricePolicy:
      type: object
      properties:
        policy_version: { type: string }
        effective_from: { type: string, format: date-time }
        effective_to: { type: string, format: date-time }
        stacking_mode: { type: string, enum: [none, best, stackable, policy] }
        guardrails: { $ref: '#/components/schemas/DiscountGuardrails' }
        deny_sale_tags:
          type: array
          items: { type: string }
        deny_sale_variant_ids:
          type: array
          items: { type: string }
        note: { type: string }
    PriceEntry:
      type: object
      properties:
        price_entry_id: { type: string }
        status: { type: string }
        variant_id: { type: string }
        sku: { type: string }
        uom: { type: string }
        scope: { $ref: '#/components/schemas/PriceScope' }
        list_price: { $ref: '#/components/schemas/Money' }
        sell_price: { $ref: '#/components/schemas/Money' }
        effective_from: { type: string, format: date-time }
        effective_to: { type: string, format: date-time }
        policy_versions:
          type: object
          properties:
            pricing_policy_version: { type: string }
            stacking_policy_version: { type: string }
            discount_policy_version: { type: string }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
        approval: { $ref: '#/components/schemas/PriceApproval' }
        approval_history:
          type: array
          items: { $ref: '#/components/schemas/PriceApprovalHistoryEntry' }
        created_at: { type: string, format: date-time }
        revision: { type: integer }
    PriceApproval:
      type: object
      properties:
        status: { type: string, enum: [pending, approved, rejected] }
        requested_at: { type: string, format: date-time }
        requested_by: { type: string }
        requested_reason: { type: string }
        requested_reasons:
          type: array
          items: { type: string }
        approved_at: { type: string, format: date-time }
        approved_by: { type: string }
        approval_reason: { type: string }
        rejected_at: { type: string, format: date-time }
        rejected_by: { type: string }
        rejection_reason: { type: string }
    PriceApprovalHistoryEntry:
      type: object
      properties:
        status: { type: string, enum: [pending, approved, rejected] }
        at: { type: string, format: date-time }
        actor: { type: string }
        reason: { type: string }
        reasons:
          type: array
          items: { type: string }
    PriceZone:
      type: object
      properties:
        price_zone_code: { type: string }
        status: { type: string }
        name: { type: string }
        description: { type: string }
        effective_from: { type: string, format: date-time }
        effective_to: { type: string, format: date-time }
        created_at: { type: string, format: date-time }
        updated_at: { type: string, format: date-time }
        revision: { type: integer }
    PriceZoneDraft:
      type: object
      properties:
        request_context: { $ref: '#/components/schemas/RequestContext' }
        reason: { type: string }
        price_zone_code: { type: string }
        status: { type: string }
        name: { type: string }
        description: { type: string }
        effective_from: { type: string, format: date-time }
        effective_to: { type: string, format: date-time }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
      required: [request_context, reason, price_zone_code, source_refs]
    PriceZoneAssignment:
      type: object
      properties:
        logical_guid: { type: string }
        price_zone_code: { type: string }
        status: { type: string }
        created_at: { type: string, format: date-time }
        updated_at: { type: string, format: date-time }
        revision: { type: integer }
    PriceList:
      type: object
      properties:
        price_list_code: { type: string }
        status: { type: string }
        name: { type: string }
        description: { type: string }
        scope: { $ref: '#/components/schemas/PriceScope' }
        effective_from: { type: string, format: date-time }
        effective_to: { type: string, format: date-time }
        created_at: { type: string, format: date-time }
        updated_at: { type: string, format: date-time }
        revision: { type: integer }
    PriceListDraft:
      type: object
      properties:
        request_context: { $ref: '#/components/schemas/RequestContext' }
        reason: { type: string }
        price_list_code: { type: string }
        status: { type: string }
        name: { type: string }
        description: { type: string }
        scope: { $ref: '#/components/schemas/PriceScope' }
        effective_from: { type: string, format: date-time }
        effective_to: { type: string, format: date-time }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
      required: [request_context, reason, price_list_code, source_refs]
    PriceListAssignment:
      type: object
      properties:
        customer_ref: { type: string }
        price_list_code: { type: string }
        channel_code: { type: string }
        logical_guid: { type: string }
        status: { type: string }
        effective_from: { type: string, format: date-time }
        effective_to: { type: string, format: date-time }
        priority: { type: number }
        created_at: { type: string, format: date-time }
        updated_at: { type: string, format: date-time }
        revision: { type: integer }
    PriceListAssignmentDraft:
      type: object
      properties:
        customer_ref: { type: string }
        price_list_code: { type: string }
        channel_code: { type: string }
        logical_guid: { type: string }
        status: { type: string }
        effective_from: { type: string, format: date-time }
        effective_to: { type: string, format: date-time }
        priority: { type: number }
        reason: { type: string }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
      required: [customer_ref, price_list_code]
    PriceEntryDraft:
      type: object
      properties:
        request_context: { $ref: '#/components/schemas/RequestContext' }
        policy_refs: { $ref: '#/components/schemas/PolicyRefs' }
        reason: { type: string }
        variant_id: { type: string }
        sku: { type: string }
        uom: { type: string }
        scope: { $ref: '#/components/schemas/PriceScope' }
        list_price: { $ref: '#/components/schemas/Money' }
        sell_price: { $ref: '#/components/schemas/Money' }
        effective_from: { type: string, format: date-time }
        effective_to: { type: string, format: date-time }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
        approval: { $ref: '#/components/schemas/PriceApproval' }
        approval_history:
          type: array
          items: { $ref: '#/components/schemas/PriceApprovalHistoryEntry' }
        notes: { type: string }
      required: [request_context, reason, source_refs]
    DynamicPricingAdjustment:
      type: object
      properties:
        type: { type: string, enum: [multiplier, amount_delta, set_price] }
        multiplier: { type: number }
        amount_delta: { $ref: '#/components/schemas/Money' }
        set_price: { $ref: '#/components/schemas/Money' }
      required: [type]
    DynamicPricingAppliesTo:
      type: object
      properties:
        variant_ids:
          type: array
          items: { type: string }
        skus:
          type: array
          items: { type: string }
    DynamicPricingRule:
      type: object
      properties:
        rule_id: { type: string }
        status: { type: string }
        name: { type: string }
        scope: { $ref: '#/components/schemas/PriceScope' }
        applies_to: { $ref: '#/components/schemas/DynamicPricingAppliesTo' }
        adjustment: { $ref: '#/components/schemas/DynamicPricingAdjustment' }
        effective_from: { type: string, format: date-time }
        effective_to: { type: string, format: date-time }
        policy_refs: { $ref: '#/components/schemas/PolicyRefs' }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
        created_at: { type: string, format: date-time }
        updated_at: { type: string, format: date-time }
        revision: { type: integer }
    DynamicPricingRuleDraft:
      type: object
      properties:
        request_context: { $ref: '#/components/schemas/RequestContext' }
        policy_refs: { $ref: '#/components/schemas/PolicyRefs' }
        reason: { type: string }
        rule_id: { type: string }
        status: { type: string }
        name: { type: string }
        scope: { $ref: '#/components/schemas/PriceScope' }
        applies_to: { $ref: '#/components/schemas/DynamicPricingAppliesTo' }
        adjustment: { $ref: '#/components/schemas/DynamicPricingAdjustment' }
        effective_from: { type: string, format: date-time }
        effective_to: { type: string, format: date-time }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
        notes: { type: string }
      required: [request_context, reason, source_refs, adjustment]
    PriceRecommendationDecision:
      type: object
      properties:
        status: { type: string }
        decided_at: { type: string, format: date-time }
        decided_by: { type: string }
        reason: { type: string }
        notes: { type: string }
    PriceRecommendationApproval:
      type: object
      properties:
        status: { type: string }
        requested_at: { type: string, format: date-time }
        requested_by: { type: string }
        requested_reason: { type: string }
        requested_reasons:
          type: array
          items: { type: string }
        approved_at: { type: string, format: date-time }
        approved_by: { type: string }
        approval_reason: { type: string }
        rejected_at: { type: string, format: date-time }
        rejected_by: { type: string }
        rejection_reason: { type: string }
    PriceRecommendationRationale:
      type: object
      properties:
        code: { type: string }
        message: { type: string }
        weight: { type: number }
        inputs:
          type: object
          additionalProperties: true
      additionalProperties: true
    PriceRecommendation:
      type: object
      properties:
        recommendation_id: { type: string }
        status: { type: string }
        recommendation_type: { type: string }
        variant_id: { type: string }
        sku: { type: string }
        scope: { $ref: '#/components/schemas/PriceScope' }
        recommended_price: { $ref: '#/components/schemas/Money' }
        current_price: { $ref: '#/components/schemas/Money' }
        list_price: { $ref: '#/components/schemas/Money' }
        delta: { $ref: '#/components/schemas/Money' }
        effective_from: { type: string, format: date-time }
        effective_to: { type: string, format: date-time }
        recommended_at: { type: string, format: date-time }
        approval_required: { type: boolean }
        approval_reasons:
          type: array
          items: { type: string }
        approval: { $ref: '#/components/schemas/PriceRecommendationApproval' }
        decision: { $ref: '#/components/schemas/PriceRecommendationDecision' }
        rationale:
          type: array
          items: { $ref: '#/components/schemas/PriceRecommendationRationale' }
        inputs:
          type: object
          additionalProperties: true
        policy_refs: { $ref: '#/components/schemas/PolicyRefs' }
        created_at: { type: string, format: date-time }
        updated_at: { type: string, format: date-time }
        revision: { type: integer }
      required: [recommendation_id, status, variant_id, recommended_price]
    PriceRecommendationDraft:
      type: object
      properties:
        request_context: { $ref: '#/components/schemas/RequestContext' }
        policy_refs: { $ref: '#/components/schemas/PolicyRefs' }
        reason: { type: string }
        recommendation_id: { type: string }
        status: { type: string }
        recommendation_type: { type: string }
        variant_id: { type: string }
        sku: { type: string }
        scope: { $ref: '#/components/schemas/PriceScope' }
        recommended_price: { $ref: '#/components/schemas/Money' }
        current_price: { $ref: '#/components/schemas/Money' }
        list_price: { $ref: '#/components/schemas/Money' }
        delta: { $ref: '#/components/schemas/Money' }
        effective_from: { type: string, format: date-time }
        effective_to: { type: string, format: date-time }
        recommended_at: { type: string, format: date-time }
        approval_required: { type: boolean }
        approval_reasons:
          type: array
          items: { type: string }
        approval: { $ref: '#/components/schemas/PriceRecommendationApproval' }
        decision: { $ref: '#/components/schemas/PriceRecommendationDecision' }
        rationale:
          type: array
          items: { $ref: '#/components/schemas/PriceRecommendationRationale' }
        inputs:
          type: object
          additionalProperties: true
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
        notes: { type: string }
      required: [request_context, reason, source_refs, variant_id, recommended_price]
    UomConversion:
      type: object
      properties:
        conversion_id: { type: string }
        status: { type: string }
        variant_id: { type: string }
        from_uom: { type: string }
        to_uom: { type: string }
        multiplier: { type: number }
        logical_guid: { type: string }
        effective_from: { type: string, format: date-time }
        effective_to: { type: string, format: date-time }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
        created_at: { type: string, format: date-time }
        updated_at: { type: string, format: date-time }
        revision: { type: integer }
    UomConversionDraft:
      type: object
      properties:
        request_context: { $ref: '#/components/schemas/RequestContext' }
        reason: { type: string }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
        variant_id: { type: string }
        from_uom: { type: string }
        to_uom: { type: string }
        multiplier: { type: number }
        logical_guid: { type: string }
        effective_from: { type: string, format: date-time }
        effective_to: { type: string, format: date-time }
        status: { type: string }
      required: [request_context, reason, source_refs]
    UomConversionSetRequest:
      type: object
      x-idempotency-scope: orgcode+route+idempotency_key
      x-idempotency-retention-hours: 24
      x-idempotency-replay: return_original_response
      properties:
        uom_conversion: { $ref: '#/components/schemas/UomConversionDraft' }
        idempotency_key: { $ref: '#/components/schemas/IdempotencyKey' }
        reason: { type: string }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
      required: [uom_conversion, reason, source_refs]
    UomConversionGetRequest:
      type: object
      properties:
        variant_id: { type: string }
        from_uom: { type: string }
        to_uom: { type: string }
        logical_guid: { type: string }
      required: [variant_id, from_uom, to_uom]
    UomConversionListRequest:
      type: object
      properties:
        variant_id: { type: string }
        from_uom: { type: string }
        to_uom: { type: string }
        logical_guid: { type: string }
        status: { type: string }
        limit: { type: integer }
        next_token: { type: string }
      required: [variant_id]
    PromotionSelectors:
      type: object
      properties:
        variant_ids:
          type: array
          items: { type: string }
        skus:
          type: array
          items: { type: string }
        brand_ids:
          type: array
          items: { type: string }
        category_ids:
          type: array
          items: { type: string }
        tags:
          type: array
          items: { type: string }
        group_codes:
          type: array
          items: { type: string }
    PromotionEligibility:
      type: object
      properties:
        channel_codes:
          type: array
          items: { type: string }
        logical_guids:
          type: array
          items: { type: string }
        price_zone_codes:
          type: array
          items: { type: string }
        price_list_codes:
          type: array
          items: { type: string }
        customer_tiers:
          type: array
          items: { type: string }
        customer_refs:
          type: array
          items: { type: string }
        price_level_codes:
          type: array
          items: { type: string }
        influencer_tiers:
          type: array
          items: { type: string }
        employee_only: { type: boolean }
        min_qty: { type: number }
        min_subtotal: { $ref: '#/components/schemas/Money' }
        max_qty: { type: number }
        max_discount_amount: { $ref: '#/components/schemas/Money' }
        exclude_sale_items: { type: boolean }
        exclude_discounted: { type: boolean }
        selectors: { $ref: '#/components/schemas/PromotionSelectors' }
    PromotionTier:
      type: object
      properties:
        min_qty: { type: number }
        min_subtotal: { $ref: '#/components/schemas/Money' }
        percent: { type: number }
        amount: { $ref: '#/components/schemas/Money' }
        fixed_price: { $ref: '#/components/schemas/Money' }
    PromotionBenefit:
      type: object
      properties:
        percent: { type: number }
        amount: { $ref: '#/components/schemas/Money' }
        fixed_price: { $ref: '#/components/schemas/Money' }
        bogo_buy_qty: { type: number }
        bogo_get_qty: { type: number }
        bogo:
          type: object
          properties:
            buy_qty: { type: number }
            get_qty: { type: number }
            get_percent: { type: number }
            get_amount: { $ref: '#/components/schemas/Money' }
            get_fixed_price: { $ref: '#/components/schemas/Money' }
        mix_match:
          type: object
          properties:
            group_qty: { type: number }
            percent: { type: number }
            amount: { $ref: '#/components/schemas/Money' }
            fixed_price: { $ref: '#/components/schemas/Money' }
        bundle:
          type: object
          properties:
            bundle_qty: { type: number }
            bundle_price: { $ref: '#/components/schemas/Money' }
            percent: { type: number }
            amount: { $ref: '#/components/schemas/Money' }
            fixed_price: { $ref: '#/components/schemas/Money' }
        tiers:
          type: array
          items: { $ref: '#/components/schemas/PromotionTier' }
    PromotionRestrictions:
      type: object
      properties:
        min_qty: { type: number }
        min_subtotal: { $ref: '#/components/schemas/Money' }
        max_qty: { type: number }
        max_discount_amount: { $ref: '#/components/schemas/Money' }
        exclude_sale_items: { type: boolean }
        exclude_discounted: { type: boolean }
    Promotion:
      type: object
      properties:
        promotion_id: { type: string }
        status: { type: string }
        name: { type: string }
        code: { type: string }
        type: { type: string, enum: [percent, amount, fixed_price, bogo, bundle, tiered, mix_match] }
        stackable: { type: boolean }
        priority: { type: integer }
        eligibility: { $ref: '#/components/schemas/PromotionEligibility' }
        benefit: { $ref: '#/components/schemas/PromotionBenefit' }
        restrictions: { $ref: '#/components/schemas/PromotionRestrictions' }
        effective_from: { type: string, format: date-time }
        effective_to: { type: string, format: date-time }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
        created_at: { type: string, format: date-time }
        revision: { type: integer }
    PromotionDraft:
      type: object
      properties:
        request_context: { $ref: '#/components/schemas/RequestContext' }
        policy_refs: { $ref: '#/components/schemas/PolicyRefs' }
        reason: { type: string }
        name: { type: string }
        code: { type: string }
        type: { type: string, enum: [percent, amount, fixed_price, bogo, bundle, tiered, mix_match] }
        stackable: { type: boolean }
        priority: { type: integer }
        eligibility: { $ref: '#/components/schemas/PromotionEligibility' }
        benefit: { $ref: '#/components/schemas/PromotionBenefit' }
        restrictions: { $ref: '#/components/schemas/PromotionRestrictions' }
        effective_from: { type: string, format: date-time }
        effective_to: { type: string, format: date-time }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
        notes: { type: string }
      required: [request_context, reason, source_refs]
    DiscountApplication:
      type: object
      properties:
        source: { type: string, enum: [promo, coupon, loyalty, manual, tier, employee, influencer, other] }
        code: { type: string }
        promotion_id: { type: string }
        amount: { $ref: '#/components/schemas/Money' }
        percent: { type: number }
        description: { type: string }
    DynamicPricingSnapshot:
      type: object
      properties:
        rule_id: { type: string }
        status: { type: string }
        adjustment: { $ref: '#/components/schemas/DynamicPricingAdjustment' }
        base_price_before: { $ref: '#/components/schemas/Money' }
        base_price_after: { $ref: '#/components/schemas/Money' }
        delta: { $ref: '#/components/schemas/Money' }
        guardrail_reasons:
          type: array
          items: { type: string }
        guardrail_min_price: { $ref: '#/components/schemas/Money' }
        guardrail_max_price: { $ref: '#/components/schemas/Money' }
    PriceSnapshot:
      type: object
      properties:
        price_as_of: { type: string, format: date-time }
        price_entry_id: { type: string }
        promotion_ids:
          type: array
          items: { type: string }
        list_price: { $ref: '#/components/schemas/Money' }
        base_price: { $ref: '#/components/schemas/Money' }
        final_price: { $ref: '#/components/schemas/Money' }
        discount_total: { $ref: '#/components/schemas/Money' }
        dynamic_pricing: { $ref: '#/components/schemas/DynamicPricingSnapshot' }
        policy_versions:
          type: object
          properties:
            pricing_policy_version: { type: string }
            promotion_policy_version: { type: string }
            stacking_policy_version: { type: string }
            discount_policy_version: { type: string }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
    PriceResolveLine:
      type: object
      properties:
        line_id: { type: string }
        variant_id: { type: string }
        sku: { type: string }
        dynamic_rule_id: { type: string }
        group_code: { type: string }
        product_context: { $ref: '#/components/schemas/PriceResolveProductContext' }
        qty: { $ref: '#/components/schemas/UomQuantity' }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
      required: [qty]
    PriceResolveProductContext:
      type: object
      properties:
        brand_id: { type: string }
        category_id: { type: string }
        tags:
          type: array
          items: { type: string }
        group_code: { type: string }
    PriceResolveResult:
      type: object
      properties:
        line_id: { type: string }
        variant_id: { type: string }
        sku: { type: string }
        qty: { $ref: '#/components/schemas/UomQuantity' }
        snapshot: { $ref: '#/components/schemas/PriceSnapshot' }
        discounts:
          type: array
          items: { $ref: '#/components/schemas/DiscountApplication' }
        approval_required: { type: boolean }
        approval_reasons:
          type: array
          items: { type: string }
        line_total: { $ref: '#/components/schemas/Money' }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
      required: [qty]
    PriceTotals:
      type: object
      properties:
        subtotal: { $ref: '#/components/schemas/Money' }
        discount_total: { $ref: '#/components/schemas/Money' }
        total: { $ref: '#/components/schemas/Money' }
        approval_required: { type: boolean }
        approval_reasons:
          type: array
          items: { type: string }
    PriceEntrySetRequest:
      type: object
      x-idempotency-scope: orgcode+route+idempotency_key
      x-idempotency-retention-hours: 24
      x-idempotency-replay: return_original_response
      properties:
        price_entry: { $ref: '#/components/schemas/PriceEntryDraft' }
        idempotency_key: { $ref: '#/components/schemas/IdempotencyKey' }
        cccode: { type: string }
        expected_revision: { type: integer }
        reason: { type: string }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
      required: [price_entry, reason, source_refs]
    PriceEntryGetRequest:
      type: object
      properties:
        price_entry_id: { type: string }
      required: [price_entry_id]
    PriceEntryListRequest:
      type: object
      properties:
        status: { type: string }
        variant_id: { type: string }
        sku: { type: string }
        price_list_code: { type: string }
        price_zone_code: { type: string }
        channel_code: { type: string }
        logical_guid: { type: string }
        effective_as_of: { type: string, format: date-time }
        limit: { type: integer }
        next_token: { type: string }
    PriceApprovalSubmitRequest:
      type: object
      properties:
        price_entry_id: { type: string }
        expected_revision: { type: integer }
        approval_reasons:
          type: array
          items: { type: string }
        reason: { type: string }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
      required: [price_entry_id, expected_revision, reason, source_refs]
    PriceApprovalApproveRequest:
      type: object
      properties:
        price_entry_id: { type: string }
        expected_revision: { type: integer }
        reason: { type: string }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
      required: [price_entry_id, expected_revision, reason, source_refs]
    PriceApprovalRejectRequest:
      type: object
      properties:
        price_entry_id: { type: string }
        expected_revision: { type: integer }
        reason: { type: string }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
      required: [price_entry_id, expected_revision, reason, source_refs]
    PriceListSetRequest:
      type: object
      x-idempotency-scope: orgcode+route+idempotency_key
      x-idempotency-retention-hours: 24
      x-idempotency-replay: return_original_response
      properties:
        price_list: { $ref: '#/components/schemas/PriceListDraft' }
        idempotency_key: { $ref: '#/components/schemas/IdempotencyKey' }
        expected_revision: { type: integer }
        cccode: { type: string }
        reason: { type: string }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
      required: [price_list, reason, source_refs]
    PriceListGetRequest:
      type: object
      properties:
        price_list_code: { type: string }
      required: [price_list_code]
    PriceListListRequest:
      type: object
      properties:
        status: { type: string }
        limit: { type: integer }
        next_token: { type: string }
    PriceListStatusSetRequest:
      type: object
      properties:
        price_list_code: { type: string }
        status: { type: string }
        expected_revision: { type: integer }
        reason: { type: string }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
      required: [price_list_code, status, expected_revision, reason, source_refs]
    PriceListAssignRequest:
      type: object
      x-idempotency-scope: orgcode+route+idempotency_key
      x-idempotency-retention-hours: 24
      x-idempotency-replay: return_original_response
      properties:
        assignment: { $ref: '#/components/schemas/PriceListAssignmentDraft' }
        idempotency_key: { $ref: '#/components/schemas/IdempotencyKey' }
        expected_revision: { type: integer }
        cccode: { type: string }
        reason: { type: string }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
      required: [assignment, reason, source_refs]
    PriceListAssignClearRequest:
      type: object
      properties:
        customer_ref: { type: string }
        price_list_code: { type: string }
        channel_code: { type: string }
        logical_guid: { type: string }
        expected_revision: { type: integer }
        reason: { type: string }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
      required: [customer_ref, price_list_code, expected_revision, reason, source_refs]
    PriceListResolveRequest:
      type: object
      properties:
        customer_ref: { type: string }
        channel_code: { type: string }
        logical_guid: { type: string }
        as_of_utc: { type: string, format: date-time }
      required: [customer_ref]
    PriceListAssignmentsRequest:
      type: object
      properties:
        customer_ref: { type: string }
        price_list_code: { type: string }
        limit: { type: integer }
        next_token: { type: string }
    PriceZoneSetRequest:
      type: object
      x-idempotency-scope: orgcode+route+idempotency_key
      x-idempotency-retention-hours: 24
      x-idempotency-replay: return_original_response
      properties:
        price_zone: { $ref: '#/components/schemas/PriceZoneDraft' }
        idempotency_key: { $ref: '#/components/schemas/IdempotencyKey' }
        expected_revision: { type: integer }
        cccode: { type: string }
        reason: { type: string }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
      required: [price_zone, reason, source_refs]
    PriceZoneGetRequest:
      type: object
      properties:
        price_zone_code: { type: string }
      required: [price_zone_code]
    PriceZoneListRequest:
      type: object
      properties:
        status: { type: string }
        limit: { type: integer }
        next_token: { type: string }
    PriceZoneStatusSetRequest:
      type: object
      properties:
        price_zone_code: { type: string }
        status: { type: string }
        expected_revision: { type: integer }
        reason: { type: string }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
      required: [price_zone_code, status, expected_revision, reason, source_refs]
    PriceZoneAssignRequest:
      type: object
      x-idempotency-scope: orgcode+route+idempotency_key
      x-idempotency-retention-hours: 24
      x-idempotency-replay: return_original_response
      properties:
        logical_guid: { type: string }
        price_zone_code: { type: string }
        expected_revision: { type: integer }
        idempotency_key: { $ref: '#/components/schemas/IdempotencyKey' }
        reason: { type: string }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
      required: [logical_guid, price_zone_code, reason, source_refs]
    PriceZoneAssignClearRequest:
      type: object
      properties:
        logical_guid: { type: string }
        expected_revision: { type: integer }
        reason: { type: string }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
      required: [logical_guid, expected_revision, reason, source_refs]
    PriceZoneResolveRequest:
      type: object
      properties:
        logical_guid: { type: string }
      required: [logical_guid]
    PriceZoneAssignmentsRequest:
      type: object
      properties:
        logical_guid: { type: string }
        price_zone_code: { type: string }
        limit: { type: integer }
        next_token: { type: string }
    DynamicPricingRuleSetRequest:
      type: object
      x-idempotency-scope: orgcode+route+idempotency_key
      x-idempotency-retention-hours: 24
      x-idempotency-replay: return_original_response
      properties:
        dynamic_rule: { $ref: '#/components/schemas/DynamicPricingRuleDraft' }
        idempotency_key: { $ref: '#/components/schemas/IdempotencyKey' }
        cccode: { type: string }
        reason: { type: string }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
      required: [dynamic_rule, reason, source_refs]
    DynamicPricingRuleGetRequest:
      type: object
      properties:
        rule_id: { type: string }
      required: [rule_id]
    DynamicPricingRuleListRequest:
      type: object
      properties:
        status: { type: string }
        channel_code: { type: string }
        logical_guid: { type: string }
        effective_as_of: { type: string, format: date-time }
        limit: { type: integer }
        next_token: { type: string }
    DynamicPricingRuleStatusSetRequest:
      type: object
      properties:
        rule_id: { type: string }
        status: { type: string }
        expected_revision: { type: integer }
        reason: { type: string }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
      required: [rule_id, status, reason, source_refs]
    PriceRecommendationSetRequest:
      type: object
      x-idempotency-scope: orgcode+route+idempotency_key
      x-idempotency-retention-hours: 24
      x-idempotency-replay: return_original_response
      properties:
        recommendation: { $ref: '#/components/schemas/PriceRecommendationDraft' }
        idempotency_key: { $ref: '#/components/schemas/IdempotencyKey' }
        cccode: { type: string }
        expected_revision: { type: integer }
        reason: { type: string }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
      required: [recommendation, reason, source_refs]
    PriceRecommendationGetRequest:
      type: object
      properties:
        recommendation_id: { type: string }
      required: [recommendation_id]
    PriceRecommendationListRequest:
      type: object
      properties:
        status: { type: string }
        variant_id: { type: string }
        channel_code: { type: string }
        logical_guid: { type: string }
        effective_as_of: { type: string, format: date-time }
        limit: { type: integer }
        next_token: { type: string }
    PriceRecommendationStatusSetRequest:
      type: object
      properties:
        recommendation_id: { type: string }
        status: { type: string }
        expected_revision: { type: integer }
        reason: { type: string }
        decision_notes: { type: string }
        approval_reasons:
          type: array
          items: { type: string }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
      required: [recommendation_id, status, expected_revision, reason, source_refs]
    PricePolicySetRequest:
      type: object
      properties:
        policy: { $ref: '#/components/schemas/PricePolicy' }
        reason: { type: string }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
      required: [policy, reason, source_refs]
    PricePolicyGetRequest:
      type: object
      properties:
        policy_version: { type: string }
        effective_as_of: { type: string, format: date-time }
    PromotionCreateRequest:
      type: object
      x-idempotency-scope: orgcode+route+idempotency_key
      x-idempotency-retention-hours: 24
      x-idempotency-replay: return_original_response
      properties:
        promotion: { $ref: '#/components/schemas/PromotionDraft' }
        idempotency_key: { $ref: '#/components/schemas/IdempotencyKey' }
        cccode: { type: string }
        reason: { type: string }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
      required: [promotion, reason, source_refs]
    PromotionEndRequest:
      type: object
      properties:
        promotion_id: { type: string }
        expected_revision: { type: integer }
        reason: { type: string }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
      required: [promotion_id, reason, source_refs]
    PromotionGetRequest:
      type: object
      properties:
        promotion_id: { type: string }
      required: [promotion_id]
    PromotionListRequest:
      type: object
      properties:
        status: { type: string }
        code: { type: string }
        active_at: { type: string, format: date-time }
        limit: { type: integer }
        next_token: { type: string }
    PriceResolveRequest:
      type: object
      properties:
        lines:
          type: array
          items: { $ref: '#/components/schemas/PriceResolveLine' }
        as_of_utc: { type: string, format: date-time }
        customer_ref: { type: string }
        customer_tier: { type: string }
        price_level_code: { type: string }
        price_zone_code: { type: string }
        price_list_code: { type: string }
        influencer_tier: { type: string }
        employee_price: { type: boolean }
        discount_codes:
          type: array
          items: { type: string }
        tender_codes:
          type: array
          items: { type: string }
        quote_mode: { type: boolean }
        apply_loyalty: { type: boolean }
        cccode: { type: string }
        reason: { type: string }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
      required: [lines, reason, source_refs]
    PriceEntryEnvelope:
      allOf:
        - { $ref: '#/components/schemas/Envelope' }
        - type: object
          properties:
            data:
              type: object
              properties:
                price_entry: { $ref: '#/components/schemas/PriceEntry' }
              required: [price_entry]
    PriceEntryListEnvelope:
      allOf:
        - { $ref: '#/components/schemas/Envelope' }
        - type: object
          properties:
            data:
              type: object
              properties:
                price_entries:
                  type: array
                  items: { $ref: '#/components/schemas/PriceEntry' }
                next_token: { type: string }
              required: [price_entries]
    PriceListEnvelope:
      allOf:
        - { $ref: '#/components/schemas/Envelope' }
        - type: object
          properties:
            data:
              type: object
              properties:
                price_list: { $ref: '#/components/schemas/PriceList' }
              required: [price_list]
    PriceListListEnvelope:
      allOf:
        - { $ref: '#/components/schemas/Envelope' }
        - type: object
          properties:
            data:
              type: object
              properties:
                price_lists:
                  type: array
                  items: { $ref: '#/components/schemas/PriceList' }
                next_token: { type: string }
              required: [price_lists]
    PriceListAssignmentEnvelope:
      allOf:
        - { $ref: '#/components/schemas/Envelope' }
        - type: object
          properties:
            data:
              type: object
              properties:
                assignment: { $ref: '#/components/schemas/PriceListAssignment' }
                cleared: { type: boolean }
              required: [assignment]
    PriceListAssignmentListEnvelope:
      allOf:
        - { $ref: '#/components/schemas/Envelope' }
        - type: object
          properties:
            data:
              type: object
              properties:
                assignments:
                  type: array
                  items: { $ref: '#/components/schemas/PriceListAssignment' }
                next_token: { type: string }
              required: [assignments]
    PriceZoneEnvelope:
      allOf:
        - { $ref: '#/components/schemas/Envelope' }
        - type: object
          properties:
            data:
              type: object
              properties:
                price_zone: { $ref: '#/components/schemas/PriceZone' }
              required: [price_zone]
    PriceZoneListEnvelope:
      allOf:
        - { $ref: '#/components/schemas/Envelope' }
        - type: object
          properties:
            data:
              type: object
              properties:
                price_zones:
                  type: array
                  items: { $ref: '#/components/schemas/PriceZone' }
                next_token: { type: string }
              required: [price_zones]
    PriceZoneAssignmentEnvelope:
      allOf:
        - { $ref: '#/components/schemas/Envelope' }
        - type: object
          properties:
            data:
              type: object
              properties:
                assignment: { $ref: '#/components/schemas/PriceZoneAssignment' }
                cleared: { type: boolean }
              required: [assignment]
    PriceZoneAssignmentListEnvelope:
      allOf:
        - { $ref: '#/components/schemas/Envelope' }
        - type: object
          properties:
            data:
              type: object
              properties:
                assignments:
                  type: array
                  items: { $ref: '#/components/schemas/PriceZoneAssignment' }
                next_token: { type: string }
              required: [assignments]
    DynamicPricingRuleEnvelope:
      allOf:
        - { $ref: '#/components/schemas/Envelope' }
        - type: object
          properties:
            data:
              type: object
              properties:
                dynamic_rule: { $ref: '#/components/schemas/DynamicPricingRule' }
              required: [dynamic_rule]
    DynamicPricingRuleListEnvelope:
      allOf:
        - { $ref: '#/components/schemas/Envelope' }
        - type: object
          properties:
            data:
              type: object
              properties:
                dynamic_rules:
                  type: array
                  items: { $ref: '#/components/schemas/DynamicPricingRule' }
                next_token: { type: string }
              required: [dynamic_rules]
    PriceRecommendationEnvelope:
      allOf:
        - { $ref: '#/components/schemas/Envelope' }
        - type: object
          properties:
            data:
              type: object
              properties:
                recommendation: { $ref: '#/components/schemas/PriceRecommendation' }
              required: [recommendation]
    PriceRecommendationListEnvelope:
      allOf:
        - { $ref: '#/components/schemas/Envelope' }
        - type: object
          properties:
            data:
              type: object
              properties:
                recommendations:
                  type: array
                  items: { $ref: '#/components/schemas/PriceRecommendation' }
                next_token: { type: string }
              required: [recommendations]
    UomConversionEnvelope:
      allOf:
        - { $ref: '#/components/schemas/Envelope' }
        - type: object
          properties:
            data:
              type: object
              properties:
                uom_conversion: { $ref: '#/components/schemas/UomConversion' }
              required: [uom_conversion]
    UomConversionListEnvelope:
      allOf:
        - { $ref: '#/components/schemas/Envelope' }
        - type: object
          properties:
            data:
              type: object
              properties:
                uom_conversions:
                  type: array
                  items: { $ref: '#/components/schemas/UomConversion' }
                next_token: { type: string }
              required: [uom_conversions]
    PricePolicyEnvelope:
      allOf:
        - { $ref: '#/components/schemas/Envelope' }
        - type: object
          properties:
            data:
              type: object
              properties:
                policy: { $ref: '#/components/schemas/PricePolicy' }
              required: [policy]
    PromotionEnvelope:
      allOf:
        - { $ref: '#/components/schemas/Envelope' }
        - type: object
          properties:
            data:
              type: object
              properties:
                promotion: { $ref: '#/components/schemas/Promotion' }
              required: [promotion]
    PromotionListEnvelope:
      allOf:
        - { $ref: '#/components/schemas/Envelope' }
        - type: object
          properties:
            data:
              type: object
              properties:
                promotions:
                  type: array
                  items: { $ref: '#/components/schemas/Promotion' }
                next_token: { type: string }
              required: [promotions]
    PriceResolveEnvelope:
      allOf:
        - { $ref: '#/components/schemas/Envelope' }
        - type: object
          properties:
            data:
              type: object
              properties:
                resolved_at: { type: string, format: date-time }
                resolved_scope: { $ref: '#/components/schemas/PriceScope' }
                policy_versions:
                  type: object
                  properties:
                    pricing_policy_version: { type: string }
                    promotion_policy_version: { type: string }
                    stacking_policy_version: { type: string }
                    discount_policy_version: { type: string }
                items:
                  type: array
                  items: { $ref: '#/components/schemas/PriceResolveResult' }
                totals: { $ref: '#/components/schemas/PriceTotals' }
              required: [items]
    CommentAttachment:
      type: object
      properties:
        mrs_guid: { type: string }
        caption: { type: string }
        filename: { type: string }
        content_type: { type: string }
        size_bytes: { type: integer, minimum: 0 }
      required: [mrs_guid]
    Comment:
      type: object
      properties:
        comment_id: { type: string }
        target_type: { type: string }
        target_id: { type: string }
        parent_comment_id: { type: string }
        caption: { type: string }
        body: { type: string }
        attachments:
          type: array
          items: { $ref: '#/components/schemas/CommentAttachment' }
        total_size_bytes: { type: integer }
        hashtags:
          type: array
          items: { type: string }
        mentions_users:
          type: array
          items: { type: string }
        mentions_teams:
          type: array
          items: { type: string }
        status:
          type: string
          enum: [current, archived, doomed, all]
          default: current
          description: Default current; use all to include archived/doomed.
        current_revision: { type: integer }
        created_at: { type: string, format: date-time }
        updated_at: { type: string, format: date-time }
        author_guid: { type: string }
      required: [comment_id, target_type, target_id, status, current_revision, created_at]
    CommentAddRequest:
      type: object
      x-idempotency-scope: orgcode+route+idempotency_key
      x-idempotency-retention-hours: 24
      x-idempotency-replay: return_original_response
      properties:
        target_type: { type: string }
        target_id: { type: string }
        parent_comment_id: { type: string }
        caption: { type: string }
        body: { type: string }
        attachments:
          type: array
          items: { $ref: '#/components/schemas/CommentAttachment' }
        hashtags:
          type: array
          items: { type: string }
        mentions_users:
          type: array
          items: { type: string }
        mentions_teams:
          type: array
          items: { type: string }
        idempotency_key: { $ref: '#/components/schemas/IdempotencyKey' }
      required: [target_type, target_id]
    CommentGetRequest:
      type: object
      properties:
        comment_id: { type: string }
        target_type: { type: string }
        target_id: { type: string }
      required: [comment_id, target_type, target_id]
    CommentListRequest:
      type: object
      properties:
        target_type: { type: string }
        target_id: { type: string }
        user_guid: { type: string }
        org_wide: { type: boolean }
        status: { type: string, enum: [current, archived, doomed, all] }
        hashtag: { type: string }
        created_after: { type: string, format: date-time }
        created_before: { type: string, format: date-time }
        limit: { type: integer, minimum: 1, maximum: 100 }
        next_token: { type: string }
      description: Requires target_type+target_id, user_guid, or org_wide=true. Defaults to status=current; use status=all to include archived/doomed.
    CommentReviseRequest:
      type: object
      properties:
        comment_id: { type: string }
        target_type: { type: string }
        target_id: { type: string }
        caption: { type: string }
        body: { type: string }
        attachments:
          type: array
          items: { $ref: '#/components/schemas/CommentAttachment' }
        hashtags:
          type: array
          items: { type: string }
        mentions_users:
          type: array
          items: { type: string }
        mentions_teams:
          type: array
          items: { type: string }
        expected_revision: { type: integer }
      required: [comment_id, target_type, target_id]
    CommentStatusRequest:
      type: object
      properties:
        comment_id: { type: string }
        target_type: { type: string }
        target_id: { type: string }
        status: { type: string, enum: [current, archived, doomed] }
      required: [comment_id, target_type, target_id, status]
    CommentReportRequest:
      type: object
      properties:
        limit: { type: integer, minimum: 1, maximum: 100 }
    CommentEnvelope:
      allOf:
        - { $ref: '#/components/schemas/Envelope' }
        - type: object
          properties:
            data:
              type: object
              properties:
                comment: { $ref: '#/components/schemas/Comment' }
              required: [comment]
    CommentListEnvelope:
      allOf:
        - { $ref: '#/components/schemas/Envelope' }
        - type: object
          properties:
            data:
              type: object
              properties:
                items:
                  type: array
                  items: { $ref: '#/components/schemas/Comment' }
                next_token: { type: string }
              required: [items]
    CommentReportEnvelope:
      allOf:
        - { $ref: '#/components/schemas/Envelope' }
        - type: object
          properties:
            data:
              type: object
              properties:
                items:
                  type: array
                  items:
                    type: object
                    properties:
                      comment_id: { type: string }
                      target_type: { type: string }
                      target_id: { type: string }
                      total_size_bytes: { type: integer }
                      created_at: { type: string, format: date-time }
                    required: [comment_id, target_type, target_id]
              required: [items]
    InboxNotification:
      type: object
      properties:
        notification_id: { type: string }
        team_guid: { type: string }
        status:
          type: string
          enum: [inbox, archived, all]
          default: inbox
          description: Default inbox; use all to include archived.
        state: { type: string, enum: [pending, completed, deferred] }
        priority: { type: string, enum: [low, medium, high, show_stopper] }
        act_by: { type: string, format: date-time }
        record_type: { type: string }
        record_id: { type: string }
        title: { type: string }
        body: { type: string }
        created_at: { type: string, format: date-time }
        updated_at: { type: string, format: date-time }
        created_by: { type: string }
      required: [notification_id, team_guid, status, state, priority, title]
    InboxCreateRequest:
      type: object
      x-idempotency-scope: orgcode+route+idempotency_key
      x-idempotency-retention-hours: 24
      x-idempotency-replay: return_original_response
      properties:
        team_guid: { type: string }
        record_type: { type: string }
        record_id: { type: string }
        title: { type: string }
        body: { type: string }
        priority: { type: string, enum: [low, medium, high, show_stopper] }
        act_by: { type: string, format: date-time }
        idempotency_key: { $ref: '#/components/schemas/IdempotencyKey' }
      required: [team_guid, title]
    InboxGetRequest:
      type: object
      properties:
        notification_id: { type: string }
      required: [notification_id]
    InboxListRequest:
      type: object
      properties:
        team_guid: { type: string }
        org_wide: { type: boolean }
        status: { type: string, enum: [inbox, archived, all] }
        state: { type: string, enum: [pending, completed, deferred] }
        limit: { type: integer, minimum: 1, maximum: 100 }
        next_token: { type: string }
      description: Requires team_guid unless org_wide=true (owner-only). Defaults to status=inbox; use status=all to include archived.
    InboxStatusRequest:
      type: object
      properties:
        notification_id: { type: string }
        status: { type: string, enum: [inbox, archived] }
      required: [notification_id, status]
    InboxStateRequest:
      type: object
      properties:
        notification_id: { type: string }
        state: { type: string, enum: [pending, completed, deferred] }
      required: [notification_id, state]
    InboxEnvelope:
      allOf:
        - { $ref: '#/components/schemas/Envelope' }
        - type: object
          properties:
            data:
              type: object
              properties:
                notification: { $ref: '#/components/schemas/InboxNotification' }
              required: [notification]
    InboxListEnvelope:
      allOf:
        - { $ref: '#/components/schemas/Envelope' }
        - type: object
          properties:
            data:
              type: object
              properties:
                items:
                  type: array
                  items: { $ref: '#/components/schemas/InboxNotification' }
                next_token: { type: string }
              required: [items]
    SubscriptionPlan:
      type: object
      properties:
        plan_id: { type: string }
        code: { type: string }
        caption: { type: string }
        status: { type: string, enum: [draft, active, suspended, archived, doomed] }
        variant_id: { type: string, description: Optional PVM variant this plan is tied to }
        frequency: { type: string, enum: [daily, weekly, biweekly, monthly, quarterly, annually] }
        price_minor: { type: integer, description: Price in minor currency units (e.g. cents) }
        currency: { type: string }
        cycle_count: { type: integer, nullable: true, description: Number of billing cycles (null = infinite) }
        trial_cycles: { type: integer, default: 0 }
        cancellation_window_days: { type: integer, default: 0 }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
        created_at: { type: string, format: date-time }
        updated_at: { type: string, format: date-time }
        revision: { type: integer }
    SubscriptionPlanSetRequest:
      type: object
      x-idempotency-scope: orgcode+route+idempotency_key
      x-idempotency-retention-hours: 24
      x-idempotency-replay: return_original_response
      properties:
        subscription_plan:
          type: object
          properties:
            request_context: { $ref: '#/components/schemas/RequestContext' }
            plan_id: { type: string }
            code: { type: string }
            caption: { type: string }
            status: { type: string, enum: [draft, active, suspended, archived, doomed] }
            variant_id: { type: string }
            frequency: { type: string, enum: [daily, weekly, biweekly, monthly, quarterly, annually] }
            price_minor: { type: integer }
            currency: { type: string }
            cycle_count: { type: integer, nullable: true }
            trial_cycles: { type: integer }
            cancellation_window_days: { type: integer }
          required: [frequency, price_minor, currency]
        reason: { type: string }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
        idempotency_key: { type: string }
      required: [subscription_plan, reason, source_refs]
    SubscriptionPlanGetRequest:
      type: object
      properties:
        plan_id: { type: string }
      required: [plan_id]
    SubscriptionPlanListRequest:
      type: object
      properties:
        status: { type: string }
        limit: { type: integer, minimum: 1, maximum: 256, default: 8 }
        next_token: { type: string }
    SubscriptionPlanStatusSetRequest:
      type: object
      properties:
        plan_id: { type: string }
        status: { type: string, enum: [draft, active, suspended, archived, doomed] }
        reason: { type: string }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
        expected_revision: { type: integer }
      required: [plan_id, status, reason, source_refs]
    SubscriptionPlanEnvelope:
      type: object
      properties:
        success: { type: boolean }
        data:
          type: object
          properties:
            subscription_plan: { $ref: '#/components/schemas/SubscriptionPlan' }
    SubscriptionPlanListEnvelope:
      type: object
      properties:
        success: { type: boolean }
        data:
          type: object
          properties:
            subscription_plans:
              type: array
              items: { $ref: '#/components/schemas/SubscriptionPlan' }
            next_token: { type: string }
    RentalRate:
      type: object
      properties:
        rate_id: { type: string }
        code: { type: string }
        caption: { type: string }
        status: { type: string, enum: [draft, active, suspended, archived, doomed] }
        variant_id: { type: string, description: Optional PVM variant this rate is tied to }
        daily_rate_minor: { type: integer, description: Daily rental rate in minor currency units }
        weekly_rate_minor: { type: integer }
        monthly_rate_minor: { type: integer }
        currency: { type: string }
        deposit_minor: { type: integer }
        damage_waiver_minor: { type: integer }
        late_fee_daily_minor: { type: integer }
        min_duration_days: { type: integer }
        max_duration_days: { type: integer }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
        created_at: { type: string, format: date-time }
        updated_at: { type: string, format: date-time }
        revision: { type: integer }
    RentalRateSetRequest:
      type: object
      x-idempotency-scope: orgcode+route+idempotency_key
      x-idempotency-retention-hours: 24
      x-idempotency-replay: return_original_response
      properties:
        rental_rate:
          type: object
          properties:
            request_context: { $ref: '#/components/schemas/RequestContext' }
            rate_id: { type: string }
            code: { type: string }
            caption: { type: string }
            status: { type: string, enum: [draft, active, suspended, archived, doomed] }
            variant_id: { type: string }
            daily_rate_minor: { type: integer }
            weekly_rate_minor: { type: integer }
            monthly_rate_minor: { type: integer }
            currency: { type: string }
            deposit_minor: { type: integer }
            damage_waiver_minor: { type: integer }
            late_fee_daily_minor: { type: integer }
            min_duration_days: { type: integer }
            max_duration_days: { type: integer }
          required: [daily_rate_minor, currency]
        reason: { type: string }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
        idempotency_key: { type: string }
      required: [rental_rate, reason, source_refs]
    RentalRateGetRequest:
      type: object
      properties:
        rate_id: { type: string }
      required: [rate_id]
    RentalRateListRequest:
      type: object
      properties:
        status: { type: string }
        limit: { type: integer, minimum: 1, maximum: 256, default: 8 }
        next_token: { type: string }
    RentalRateStatusSetRequest:
      type: object
      properties:
        rate_id: { type: string }
        status: { type: string, enum: [draft, active, suspended, archived, doomed] }
        reason: { type: string }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
        expected_revision: { type: integer }
      required: [rate_id, status, reason, source_refs]
    RentalRateEnvelope:
      type: object
      properties:
        success: { type: boolean }
        data:
          type: object
          properties:
            rental_rate: { $ref: '#/components/schemas/RentalRate' }
    RentalRateListEnvelope:
      type: object
      properties:
        success: { type: boolean }
        data:
          type: object
          properties:
            rental_rates:
              type: array
              items: { $ref: '#/components/schemas/RentalRate' }
            next_token: { type: string }
    FxRate:
      type: object
      properties:
        fx_rate_id: { type: string }
        base_currency: { type: string, description: ISO 4217 3-letter currency code }
        target_currency: { type: string, description: ISO 4217 3-letter currency code }
        rate: { type: number, description: Exchange rate (base → target) }
        effective_from: { type: string, format: date-time }
        effective_to: { type: string, format: date-time, nullable: true }
        source: { type: string, description: 'Rate source (manual, xe.com, ecb, etc.)' }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
        reason: { type: string }
        created_at: { type: string, format: date-time }
        updated_at: { type: string, format: date-time }
        revision: { type: integer }
    FxRateSetRequest:
      type: object
      x-idempotency-scope: orgcode+route+idempotency_key
      x-idempotency-retention-hours: 24
      x-idempotency-replay: return_original_response
      properties:
        fx_rate:
          type: object
          properties:
            fx_rate_id: { type: string, description: Optional for upsert }
            base_currency: { type: string }
            target_currency: { type: string }
            rate: { type: number }
            effective_from: { type: string, format: date-time }
            effective_to: { type: string, format: date-time }
            source: { type: string, default: manual }
          required: [base_currency, target_currency, rate, effective_from]
        reason: { type: string }
        source_refs: { $ref: '#/components/schemas/SourceRefs' }
        idempotency_key: { type: string }
      required: [fx_rate, reason, source_refs]
    FxRateGetRequest:
      type: object
      description: Provide fx_rate_id for direct lookup, or base_currency + target_currency (+ optional effective_as_of) for pair lookup.
      properties:
        fx_rate_id: { type: string }
        base_currency: { type: string }
        target_currency: { type: string }
        effective_as_of: { type: string, format: date-time, description: Defaults to now }
    FxRateListRequest:
      type: object
      properties:
        base_currency: { type: string }
        target_currency: { type: string }
        limit: { type: integer, minimum: 1, maximum: 256, default: 8 }
        next_token: { type: string }
    FxRateEnvelope:
      type: object
      properties:
        success: { type: boolean }
        data:
          type: object
          properties:
            fx_rate: { $ref: '#/components/schemas/FxRate' }
    FxRateListEnvelope:
      type: object
      properties:
        success: { type: boolean }
        data:
          type: object
          properties:
            fx_rates:
              type: array
              items: { $ref: '#/components/schemas/FxRate' }
            next_token: { type: string }
paths:
  /stat:
    get:
      summary: Health check
      description: |
        Health check. Tenant routes require x-orgcode; /stat health checks do not. Org-scoped reads may
        return 404 for non-associated callers (anti-enumeration). Route class Tier A (p95 500ms).
      x-route-class: Tier A
      x-qps-target: 5
      x-concurrency-target: 2
      x-latency-p95-ms: 500
      responses:
        '200':
          description: ok
          content:
            application/json:
              schema:
                allOf:
                  - { $ref: '#/components/schemas/Envelope' }
                  - type: object
                    properties:
                      data:
                        type: object
                        properties:
                          service: { type: string }
                          status: { type: string }
  /price/resolve:
    post:
      summary: Resolve price (draft)
      description: |
        Resolve price (draft). Auth is via headers; org identity uses x-orgcode or body placement as
        documented. Org-scoped reads may return 404 for non-associated callers (anti-enumeration). Route
        class Tier C (p95 150ms, p99 400ms).
      x-status: draft
      x-route-class: Tier C
      x-qps-target: 2000
      x-concurrency-target: 2500
      x-latency-p95-ms: 150
      x-latency-p99-ms: 400
      parameters:
        - { $ref: '#/components/parameters/OrgHeader' }
        - { $ref: '#/components/parameters/LogicalHeader' }
        - { $ref: '#/components/parameters/ChannelHeader' }
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/PriceResolveRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/PriceResolveEnvelope' }
  /price/set:
    post:
      summary: Create or update price entry (draft)
      description: |
        Create or update price entry (draft). Auth is via headers; org identity uses x-orgcode or body
        placement as documented. If this updates a revisioned record, expected_revision is required (428 if
        missing; 409 on mismatch). Route class Tier A (p95 500ms).
      x-status: draft
      x-route-class: Tier A
      x-qps-target: 50
      x-concurrency-target: 200
      x-latency-p95-ms: 500
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/PriceEntrySetRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/PriceEntryEnvelope' }
  /price/get:
    post:
      summary: Get price entry (draft)
      description: |
        Get price entry (draft). Auth is via headers; org identity uses x-orgcode or body placement as
        documented. Org-scoped reads may return 404 for non-associated callers (anti-enumeration). Route
        class Tier B (p95 300ms).
      x-status: draft
      x-route-class: Tier B
      x-qps-target: 300
      x-concurrency-target: 500
      x-latency-p95-ms: 300
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/PriceEntryGetRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/PriceEntryEnvelope' }
  /price/list:
    post:
      summary: List price entries (draft)
      description: |
        List price entries (draft). Auth is via headers; org identity uses x-orgcode or body placement as
        documented. Paginated with limit/next_token (default 8; clamp 1–256). Route class Tier B (p95
        300ms).
      x-status: draft
      x-route-class: Tier B
      x-qps-target: 300
      x-concurrency-target: 500
      x-latency-p95-ms: 300
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/PriceEntryListRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/PriceEntryListEnvelope' }
  /price/approval/submit:
    post:
      summary: Submit price entry for approval (draft)
      description: |
        Submit price entry for approval (draft). Auth is via headers; org identity uses x-orgcode or body
        placement as documented. If this updates a revisioned record, expected_revision is required (428 if
        missing; 409 on mismatch). Route class Tier B (p95 400ms).
      x-status: draft
      x-route-class: Tier B
      x-qps-target: 100
      x-concurrency-target: 200
      x-latency-p95-ms: 400
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/PriceApprovalSubmitRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/PriceEntryEnvelope' }
  /price/approval/approve:
    post:
      summary: Approve price entry (draft)
      description: |
        Approve price entry (draft). Auth is via headers; org identity uses x-orgcode or body placement as
        documented. If this updates a revisioned record, expected_revision is required (428 if missing; 409
        on mismatch). Route class Tier B (p95 400ms).
      x-status: draft
      x-route-class: Tier B
      x-qps-target: 100
      x-concurrency-target: 200
      x-latency-p95-ms: 400
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/PriceApprovalApproveRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/PriceEntryEnvelope' }
  /price/approval/reject:
    post:
      summary: Reject price entry (draft)
      description: |
        Reject price entry (draft). Auth is via headers; org identity uses x-orgcode or body placement as
        documented. If this updates a revisioned record, expected_revision is required (428 if missing; 409
        on mismatch). Route class Tier B (p95 400ms).
      x-status: draft
      x-route-class: Tier B
      x-qps-target: 100
      x-concurrency-target: 200
      x-latency-p95-ms: 400
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/PriceApprovalRejectRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/PriceEntryEnvelope' }
  /price-list/set:
    post:
      summary: Create or update price list (draft)
      description: |
        Create or update price list (draft). Auth is via headers; org identity uses x-orgcode or body
        placement as documented. If this updates a revisioned record, expected_revision is required (428 if
        missing; 409 on mismatch). Route class Tier A (p95 500ms).
      x-status: draft
      x-route-class: Tier A
      x-qps-target: 50
      x-concurrency-target: 200
      x-latency-p95-ms: 500
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/PriceListSetRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/PriceListEnvelope' }
  /price-list/get:
    post:
      summary: Get price list (draft)
      description: |
        Get price list (draft). Auth is via headers; org identity uses x-orgcode or body placement as
        documented. Org-scoped reads may return 404 for non-associated callers (anti-enumeration). Route
        class Tier B (p95 300ms).
      x-status: draft
      x-route-class: Tier B
      x-qps-target: 300
      x-concurrency-target: 500
      x-latency-p95-ms: 300
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/PriceListGetRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/PriceListEnvelope' }
  /price-list/list:
    post:
      summary: List price lists (draft)
      description: |
        List price lists (draft). Auth is via headers; org identity uses x-orgcode or body placement as
        documented. Paginated with limit/next_token (default 8; clamp 1–256). Route class Tier B (p95
        300ms).
      x-status: draft
      x-route-class: Tier B
      x-qps-target: 300
      x-concurrency-target: 500
      x-latency-p95-ms: 300
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/PriceListListRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/PriceListListEnvelope' }
  /price-list/status/set:
    post:
      summary: Set price list status (draft)
      description: |
        Set price list status (draft). Auth is via headers; org identity uses x-orgcode or body placement as
        documented. If this updates a revisioned record, expected_revision is required (428 if missing; 409
        on mismatch). Route class Tier A (p95 500ms).
      x-status: draft
      x-route-class: Tier A
      x-qps-target: 50
      x-concurrency-target: 200
      x-latency-p95-ms: 500
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/PriceListStatusSetRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/PriceListEnvelope' }
  /price-list/assign:
    post:
      summary: Assign price list to customer (draft)
      description: |
        Assign price list to customer (draft). Auth is via headers; org identity uses x-orgcode or body
        placement as documented. If this updates a revisioned record, expected_revision is required (428 if
        missing; 409 on mismatch). Route class Tier A (p95 500ms).
      x-status: draft
      x-route-class: Tier A
      x-qps-target: 50
      x-concurrency-target: 200
      x-latency-p95-ms: 500
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/PriceListAssignRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/PriceListAssignmentEnvelope' }
  /price-list/assign/clear:
    post:
      summary: Clear price list assignment (draft)
      description: |
        Clear price list assignment (draft). Auth is via headers; org identity uses x-orgcode or body
        placement as documented. If this updates a revisioned record, expected_revision is required (428 if
        missing; 409 on mismatch). Route class Tier A (p95 500ms).
      x-status: draft
      x-route-class: Tier A
      x-qps-target: 50
      x-concurrency-target: 200
      x-latency-p95-ms: 500
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/PriceListAssignClearRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/PriceListAssignmentEnvelope' }
  /price-list/resolve:
    post:
      summary: Resolve price list assignment (draft)
      description: |
        Resolve price list assignment (draft). Auth is via headers; org identity uses x-orgcode or body
        placement as documented. Org-scoped reads may return 404 for non-associated callers
        (anti-enumeration). Route class Tier B (p95 300ms).
      x-status: draft
      x-route-class: Tier B
      x-qps-target: 300
      x-concurrency-target: 500
      x-latency-p95-ms: 300
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/PriceListResolveRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/PriceListAssignmentEnvelope' }
  /price-list/assignments:
    post:
      summary: List price list assignments (draft)
      description: |
        List price list assignments (draft). Auth is via headers; org identity uses x-orgcode or body
        placement as documented. Paginated with limit/next_token (default 8; clamp 1–256). If this updates a
        revisioned record, expected_revision is required (428 if missing; 409 on mismatch). Route class Tier
        B (p95 300ms).
      x-status: draft
      x-route-class: Tier B
      x-qps-target: 300
      x-concurrency-target: 500
      x-latency-p95-ms: 300
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/PriceListAssignmentsRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/PriceListAssignmentListEnvelope' }
  /price-zone/set:
    post:
      summary: Create or update price zone (draft)
      description: |
        Create or update price zone (draft). Auth is via headers; org identity uses x-orgcode or body
        placement as documented. If this updates a revisioned record, expected_revision is required (428 if
        missing; 409 on mismatch). Route class Tier A (p95 500ms).
      x-status: draft
      x-route-class: Tier A
      x-qps-target: 50
      x-concurrency-target: 200
      x-latency-p95-ms: 500
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/PriceZoneSetRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/PriceZoneEnvelope' }
  /price-zone/get:
    post:
      summary: Get price zone (draft)
      description: |
        Get price zone (draft). Auth is via headers; org identity uses x-orgcode or body placement as
        documented. Org-scoped reads may return 404 for non-associated callers (anti-enumeration). Route
        class Tier B (p95 300ms).
      x-status: draft
      x-route-class: Tier B
      x-qps-target: 300
      x-concurrency-target: 500
      x-latency-p95-ms: 300
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/PriceZoneGetRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/PriceZoneEnvelope' }
  /price-zone/list:
    post:
      summary: List price zones (draft)
      description: |
        List price zones (draft). Auth is via headers; org identity uses x-orgcode or body placement as
        documented. Paginated with limit/next_token (default 8; clamp 1–256). Route class Tier B (p95
        300ms).
      x-status: draft
      x-route-class: Tier B
      x-qps-target: 300
      x-concurrency-target: 500
      x-latency-p95-ms: 300
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/PriceZoneListRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/PriceZoneListEnvelope' }
  /price-zone/status/set:
    post:
      summary: Set price zone status (draft)
      description: |
        Set price zone status (draft). Auth is via headers; org identity uses x-orgcode or body placement as
        documented. If this updates a revisioned record, expected_revision is required (428 if missing; 409
        on mismatch). Route class Tier A (p95 500ms).
      x-status: draft
      x-route-class: Tier A
      x-qps-target: 50
      x-concurrency-target: 200
      x-latency-p95-ms: 500
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/PriceZoneStatusSetRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/PriceZoneEnvelope' }
  /price-zone/assign:
    post:
      summary: Assign logical facility to price zone (draft)
      description: |
        Assign logical facility to price zone (draft). Auth is via headers; org identity uses x-orgcode or
        body placement as documented. If this updates a revisioned record, expected_revision is required
        (428 if missing; 409 on mismatch). Route class Tier A (p95 500ms).
      x-status: draft
      x-route-class: Tier A
      x-qps-target: 50
      x-concurrency-target: 200
      x-latency-p95-ms: 500
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/PriceZoneAssignRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/PriceZoneAssignmentEnvelope' }
  /price-zone/assign/clear:
    post:
      summary: Clear price zone assignment (draft)
      description: |
        Clear price zone assignment (draft). Auth is via headers; org identity uses x-orgcode or body
        placement as documented. If this updates a revisioned record, expected_revision is required (428 if
        missing; 409 on mismatch). Route class Tier A (p95 500ms).
      x-status: draft
      x-route-class: Tier A
      x-qps-target: 50
      x-concurrency-target: 200
      x-latency-p95-ms: 500
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/PriceZoneAssignClearRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/PriceZoneAssignmentEnvelope' }
  /price-zone/resolve:
    post:
      summary: Resolve price zone for logical facility (draft)
      description: |
        Resolve price zone for logical facility (draft). Auth is via headers; org identity uses x-orgcode or
        body placement as documented. Org-scoped reads may return 404 for non-associated callers
        (anti-enumeration). Route class Tier B (p95 300ms).
      x-status: draft
      x-route-class: Tier B
      x-qps-target: 300
      x-concurrency-target: 500
      x-latency-p95-ms: 300
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/PriceZoneResolveRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/PriceZoneAssignmentEnvelope' }
  /price-zone/assignments:
    post:
      summary: List price zone assignments (draft)
      description: |
        List price zone assignments (draft). Auth is via headers; org identity uses x-orgcode or body
        placement as documented. Paginated with limit/next_token (default 8; clamp 1–256). If this updates a
        revisioned record, expected_revision is required (428 if missing; 409 on mismatch). Route class Tier
        B (p95 300ms).
      x-status: draft
      x-route-class: Tier B
      x-qps-target: 300
      x-concurrency-target: 500
      x-latency-p95-ms: 300
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/PriceZoneAssignmentsRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/PriceZoneAssignmentListEnvelope' }
  /dynamic-rule/set:
    post:
      summary: Create or update dynamic pricing rule (draft)
      description: |
        Create or update dynamic pricing rule (draft). Auth is via headers; org identity uses x-orgcode or
        body placement as documented. If this updates a revisioned record, expected_revision is required
        (428 if missing; 409 on mismatch). Route class Tier A (p95 500ms).
      x-status: draft
      x-route-class: Tier A
      x-qps-target: 50
      x-concurrency-target: 200
      x-latency-p95-ms: 500
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/DynamicPricingRuleSetRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/DynamicPricingRuleEnvelope' }
  /dynamic-rule/get:
    post:
      summary: Get dynamic pricing rule (draft)
      description: |
        Get dynamic pricing rule (draft). Auth is via headers; org identity uses x-orgcode or body placement
        as documented. Org-scoped reads may return 404 for non-associated callers (anti-enumeration). Route
        class Tier B (p95 300ms).
      x-status: draft
      x-route-class: Tier B
      x-qps-target: 300
      x-concurrency-target: 500
      x-latency-p95-ms: 300
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/DynamicPricingRuleGetRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/DynamicPricingRuleEnvelope' }
  /dynamic-rule/list:
    post:
      summary: List dynamic pricing rules (draft)
      description: |
        List dynamic pricing rules (draft). Auth is via headers; org identity uses x-orgcode or body
        placement as documented. Paginated with limit/next_token (default 8; clamp 1–256). Route class Tier
        B (p95 300ms).
      x-status: draft
      x-route-class: Tier B
      x-qps-target: 300
      x-concurrency-target: 500
      x-latency-p95-ms: 300
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/DynamicPricingRuleListRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/DynamicPricingRuleListEnvelope' }
  /dynamic-rule/status/set:
    post:
      summary: Set dynamic pricing rule status (draft)
      description: |
        Set dynamic pricing rule status (draft). Auth is via headers; org identity uses x-orgcode or body
        placement as documented. If this updates a revisioned record, expected_revision is required (428 if
        missing; 409 on mismatch). Route class Tier A (p95 500ms).
      x-status: draft
      x-route-class: Tier A
      x-qps-target: 50
      x-concurrency-target: 200
      x-latency-p95-ms: 500
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/DynamicPricingRuleStatusSetRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/DynamicPricingRuleEnvelope' }
  /recommendation/set:
    post:
      summary: Create or update price recommendation (draft)
      description: |
        Create or update price recommendation (draft). Auth is via headers; org identity uses x-orgcode or
        body placement as documented. If this updates a revisioned record, expected_revision is required
        (428 if missing; 409 on mismatch). Route class Tier A (p95 500ms).
      x-status: draft
      x-route-class: Tier A
      x-qps-target: 50
      x-concurrency-target: 200
      x-latency-p95-ms: 500
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/PriceRecommendationSetRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/PriceRecommendationEnvelope' }
  /recommendation/get:
    post:
      summary: Get price recommendation (draft)
      description: |
        Get price recommendation (draft). Auth is via headers; org identity uses x-orgcode or body placement
        as documented. Org-scoped reads may return 404 for non-associated callers (anti-enumeration). Route
        class Tier B (p95 300ms).
      x-status: draft
      x-route-class: Tier B
      x-qps-target: 300
      x-concurrency-target: 500
      x-latency-p95-ms: 300
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/PriceRecommendationGetRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/PriceRecommendationEnvelope' }
  /recommendation/list:
    post:
      summary: List price recommendations (draft)
      description: |
        List price recommendations (draft). Auth is via headers; org identity uses x-orgcode or body
        placement as documented. Paginated with limit/next_token (default 8; clamp 1–256). Route class Tier
        B (p95 300ms).
      x-status: draft
      x-route-class: Tier B
      x-qps-target: 300
      x-concurrency-target: 500
      x-latency-p95-ms: 300
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/PriceRecommendationListRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/PriceRecommendationListEnvelope' }
  /recommendation/status/set:
    post:
      summary: Set price recommendation status (draft)
      description: |
        Set price recommendation status (draft). Auth is via headers; org identity uses x-orgcode or body
        placement as documented. If this updates a revisioned record, expected_revision is required (428 if
        missing; 409 on mismatch). Route class Tier A (p95 500ms).
      x-status: draft
      x-route-class: Tier A
      x-qps-target: 50
      x-concurrency-target: 200
      x-latency-p95-ms: 500
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/PriceRecommendationStatusSetRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/PriceRecommendationEnvelope' }
  /policy/get:
    post:
      summary: Get pricing policy (draft)
      description: |
        Get pricing policy (draft). Auth is via headers; org identity uses x-orgcode or body placement as
        documented. Org-scoped reads may return 404 for non-associated callers (anti-enumeration). Route
        class Tier B (p95 300ms).
      x-status: draft
      x-route-class: Tier B
      x-qps-target: 300
      x-concurrency-target: 500
      x-latency-p95-ms: 300
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/PricePolicyGetRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/PricePolicyEnvelope' }
  /policy/set:
    post:
      summary: Set pricing policy (draft)
      description: |
        Set pricing policy (draft). Auth is via headers; org identity uses x-orgcode or body placement as
        documented. If this updates a revisioned record, expected_revision is required (428 if missing; 409
        on mismatch). Route class Tier A (p95 500ms).
      x-status: draft
      x-route-class: Tier A
      x-qps-target: 50
      x-concurrency-target: 200
      x-latency-p95-ms: 500
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/PricePolicySetRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/PricePolicyEnvelope' }
  /promotion/create:
    post:
      summary: Create promotion (draft)
      description: |
        Create promotion (draft). Auth is via headers; org identity uses x-orgcode or body placement as
        documented. If this updates a revisioned record, expected_revision is required (428 if missing; 409
        on mismatch). Route class Tier A (p95 500ms).
      x-status: draft
      x-route-class: Tier A
      x-qps-target: 50
      x-concurrency-target: 200
      x-latency-p95-ms: 500
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/PromotionCreateRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/PromotionEnvelope' }
  /promotion/get:
    post:
      summary: Get promotion (draft)
      description: |
        Get promotion (draft). Auth is via headers; org identity uses x-orgcode or body placement as
        documented. Org-scoped reads may return 404 for non-associated callers (anti-enumeration). Route
        class Tier B (p95 300ms).
      x-status: draft
      x-route-class: Tier B
      x-qps-target: 300
      x-concurrency-target: 500
      x-latency-p95-ms: 300
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/PromotionGetRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/PromotionEnvelope' }
  /promotion/list:
    post:
      summary: List promotions (draft)
      description: |
        List promotions (draft). Auth is via headers; org identity uses x-orgcode or body placement as
        documented. Paginated with limit/next_token (default 8; clamp 1–256). Route class Tier B (p95
        300ms).
      x-status: draft
      x-route-class: Tier B
      x-qps-target: 300
      x-concurrency-target: 500
      x-latency-p95-ms: 300
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/PromotionListRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/PromotionListEnvelope' }
  /promotion/end:
    post:
      summary: End promotion (draft)
      description: |
        End promotion (draft). Auth is via headers; org identity uses x-orgcode or body placement as
        documented. Route class Tier A (p95 500ms).
      x-status: draft
      x-route-class: Tier A
      x-qps-target: 50
      x-concurrency-target: 200
      x-latency-p95-ms: 500
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/PromotionEndRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/PromotionEnvelope' }
  /uom/set:
    post:
      summary: Set UoM conversion (draft)
      description: |
        Set UoM conversion (draft). Auth is via headers; org identity uses x-orgcode or body placement as
        documented. If this updates a revisioned record, expected_revision is required (428 if missing; 409
        on mismatch). Route class Tier B (p95 300ms).
      x-status: draft
      x-route-class: Tier B
      x-qps-target: 300
      x-concurrency-target: 500
      x-latency-p95-ms: 300
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/UomConversionSetRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/UomConversionEnvelope' }
  /uom/get:
    post:
      summary: Get UoM conversion (draft)
      description: |
        Get UoM conversion (draft). Auth is via headers; org identity uses x-orgcode or body placement as
        documented. Org-scoped reads may return 404 for non-associated callers (anti-enumeration). Route
        class Tier B (p95 300ms).
      x-status: draft
      x-route-class: Tier B
      x-qps-target: 300
      x-concurrency-target: 500
      x-latency-p95-ms: 300
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/UomConversionGetRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/UomConversionEnvelope' }
  /uom/list:
    post:
      summary: List UoM conversions (draft)
      description: |
        List UoM conversions (draft). Auth is via headers; org identity uses x-orgcode or body placement as
        documented. Paginated with limit/next_token (default 8; clamp 1–256). Route class Tier B (p95
        300ms).
      x-status: draft
      x-route-class: Tier B
      x-qps-target: 300
      x-concurrency-target: 500
      x-latency-p95-ms: 300
      parameters: [ { $ref: '#/components/parameters/OrgHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/UomConversionListRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/UomConversionListEnvelope' }
  /comment:
    post:
      summary: Add comment (draft)
      description: |
        Add comment (draft). Auth is via headers; org identity uses x-orgcode or body placement as
        documented. Route class Tier A (p95 500ms).
      x-status: draft
      x-route-class: Tier A
      x-qps-target: 50
      x-concurrency-target: 200
      x-latency-p95-ms: 500
      parameters: [ { $ref: '#/components/parameters/OrgHeader' }, { $ref: '#/components/parameters/LogicalHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/CommentAddRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/CommentEnvelope' }
  /comment/get:
    post:
      summary: Get comment (draft)
      description: |
        Get comment (draft). Auth is via headers; org identity uses x-orgcode or body placement as
        documented. Org-scoped reads may return 404 for non-associated callers (anti-enumeration). Route
        class Tier B (p95 300ms).
      x-status: draft
      x-route-class: Tier B
      x-qps-target: 300
      x-concurrency-target: 500
      x-latency-p95-ms: 300
      parameters: [ { $ref: '#/components/parameters/OrgHeader' }, { $ref: '#/components/parameters/LogicalHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/CommentGetRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/CommentEnvelope' }
  /comment/list:
    post:
      summary: List comments (draft)
      description: |
        List comments (draft). Auth is via headers; org identity uses x-orgcode or body placement as
        documented. Paginated with limit/next_token (default 8; clamp 1–256). Route class Tier B (p95
        300ms).
      x-status: draft
      x-route-class: Tier B
      x-qps-target: 300
      x-concurrency-target: 500
      x-latency-p95-ms: 300
      parameters: [ { $ref: '#/components/parameters/OrgHeader' }, { $ref: '#/components/parameters/LogicalHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/CommentListRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/CommentListEnvelope' }
  /comment/revise:
    post:
      summary: Revise comment (draft)
      description: |
        Revise comment (draft). Auth is via headers; org identity uses x-orgcode or body placement as
        documented. Route class Tier A (p95 500ms).
      x-status: draft
      x-route-class: Tier A
      x-qps-target: 50
      x-concurrency-target: 200
      x-latency-p95-ms: 500
      parameters: [ { $ref: '#/components/parameters/OrgHeader' }, { $ref: '#/components/parameters/LogicalHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/CommentReviseRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/CommentEnvelope' }
  /comment/status:
    post:
      summary: Update comment status (draft)
      description: |
        Update comment status (draft). Auth is via headers; org identity uses x-orgcode or body placement as
        documented. If this updates a revisioned record, expected_revision is required (428 if missing; 409
        on mismatch). Route class Tier A (p95 500ms).
      x-status: draft
      x-route-class: Tier A
      x-qps-target: 50
      x-concurrency-target: 200
      x-latency-p95-ms: 500
      parameters: [ { $ref: '#/components/parameters/OrgHeader' }, { $ref: '#/components/parameters/LogicalHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/CommentStatusRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/CommentEnvelope' }
  /comment/report:
    post:
      summary: Report top-N largest comments (draft)
      description: |
        Report top-N largest comments (draft). Auth is via headers; org identity uses x-orgcode or body
        placement as documented. Route class Tier A (p95 500ms).
      x-status: draft
      x-route-class: Tier A
      x-qps-target: 50
      x-concurrency-target: 200
      x-latency-p95-ms: 500
      parameters: [ { $ref: '#/components/parameters/OrgHeader' }, { $ref: '#/components/parameters/LogicalHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/CommentReportRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/CommentReportEnvelope' }
  /inbox/create:
    post:
      summary: Create inbox notification (draft)
      description: |
        Create inbox notification (draft). Auth is via headers; org identity uses x-orgcode or body
        placement as documented. If this updates a revisioned record, expected_revision is required (428 if
        missing; 409 on mismatch). Route class Tier A (p95 500ms).
      x-status: draft
      x-route-class: Tier A
      x-qps-target: 50
      x-concurrency-target: 200
      x-latency-p95-ms: 500
      parameters: [ { $ref: '#/components/parameters/OrgHeader' }, { $ref: '#/components/parameters/LogicalHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/InboxCreateRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/InboxEnvelope' }
  /inbox/get:
    post:
      summary: Get inbox notification (draft)
      description: |
        Get inbox notification (draft). Auth is via headers; org identity uses x-orgcode or body placement
        as documented. Org-scoped reads may return 404 for non-associated callers (anti-enumeration). Route
        class Tier B (p95 300ms).
      x-status: draft
      x-route-class: Tier B
      x-qps-target: 300
      x-concurrency-target: 500
      x-latency-p95-ms: 300
      parameters: [ { $ref: '#/components/parameters/OrgHeader' }, { $ref: '#/components/parameters/LogicalHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/InboxGetRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/InboxEnvelope' }
  /inbox/list:
    post:
      summary: List inbox notifications (draft)
      description: |
        List inbox notifications (draft). Auth is via headers; org identity uses x-orgcode or body placement
        as documented. Paginated with limit/next_token (default 8; clamp 1–256). Route class Tier B (p95
        300ms).
      x-status: draft
      x-route-class: Tier B
      x-qps-target: 300
      x-concurrency-target: 500
      x-latency-p95-ms: 300
      parameters: [ { $ref: '#/components/parameters/OrgHeader' }, { $ref: '#/components/parameters/LogicalHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/InboxListRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/InboxListEnvelope' }
  /inbox/status:
    post:
      summary: Update inbox status (draft)
      description: |
        Update inbox status (draft). Auth is via headers; org identity uses x-orgcode or body placement as
        documented. If this updates a revisioned record, expected_revision is required (428 if missing; 409
        on mismatch). Route class Tier A (p95 500ms).
      x-status: draft
      x-route-class: Tier A
      x-qps-target: 50
      x-concurrency-target: 200
      x-latency-p95-ms: 500
      parameters: [ { $ref: '#/components/parameters/OrgHeader' }, { $ref: '#/components/parameters/LogicalHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/InboxStatusRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/InboxEnvelope' }
  /inbox/state:
    post:
      summary: Update inbox state (draft)
      description: |
        Update inbox state (draft). Auth is via headers; org identity uses x-orgcode or body placement as
        documented. Route class Tier A (p95 500ms).
      x-status: draft
      x-route-class: Tier A
      x-qps-target: 50
      x-concurrency-target: 200
      x-latency-p95-ms: 500
      parameters: [ { $ref: '#/components/parameters/OrgHeader' }, { $ref: '#/components/parameters/LogicalHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/InboxStateRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/InboxEnvelope' }
  /subscription-plan/set:
    post:
      operationId: subscriptionPlanSet
      summary: Create or update a subscription plan
      description: |
        Upsert a subscription plan that defines recurring pricing contracts. Auth is via headers;
        org identity uses x-orgcode or body placement as documented. Route class Tier A (p95 500ms).
      x-route-class: Tier A
      x-qps-target: 50
      x-concurrency-target: 200
      x-latency-p95-ms: 500
      parameters: [ { $ref: '#/components/parameters/OrgHeader' }, { $ref: '#/components/parameters/LogicalHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/SubscriptionPlanSetRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/SubscriptionPlanEnvelope' }
  /subscription-plan/get:
    post:
      operationId: subscriptionPlanGet
      summary: Get a subscription plan by ID
      x-route-class: Tier A
      x-qps-target: 200
      x-concurrency-target: 200
      x-latency-p95-ms: 200
      parameters: [ { $ref: '#/components/parameters/OrgHeader' }, { $ref: '#/components/parameters/LogicalHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/SubscriptionPlanGetRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/SubscriptionPlanEnvelope' }
  /subscription-plan/list:
    post:
      operationId: subscriptionPlanList
      summary: List subscription plans with optional status filter
      x-route-class: Tier A
      x-qps-target: 200
      x-concurrency-target: 200
      x-latency-p95-ms: 500
      parameters: [ { $ref: '#/components/parameters/OrgHeader' }, { $ref: '#/components/parameters/LogicalHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/SubscriptionPlanListRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/SubscriptionPlanListEnvelope' }
  /subscription-plan/status/set:
    post:
      operationId: subscriptionPlanStatusSet
      summary: Update subscription plan status
      x-route-class: Tier A
      x-qps-target: 50
      x-concurrency-target: 200
      x-latency-p95-ms: 500
      parameters: [ { $ref: '#/components/parameters/OrgHeader' }, { $ref: '#/components/parameters/LogicalHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/SubscriptionPlanStatusSetRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/SubscriptionPlanEnvelope' }
  /rental-rate/set:
    post:
      operationId: rentalRateSet
      summary: Create or update a rental rate
      x-route-class: Tier A
      x-qps-target: 50
      x-concurrency-target: 200
      x-latency-p95-ms: 500
      parameters: [ { $ref: '#/components/parameters/OrgHeader' }, { $ref: '#/components/parameters/LogicalHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/RentalRateSetRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/RentalRateEnvelope' }
  /rental-rate/get:
    post:
      operationId: rentalRateGet
      summary: Get a rental rate by ID
      x-route-class: Tier A
      x-qps-target: 200
      x-concurrency-target: 200
      x-latency-p95-ms: 200
      parameters: [ { $ref: '#/components/parameters/OrgHeader' }, { $ref: '#/components/parameters/LogicalHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/RentalRateGetRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/RentalRateEnvelope' }
  /rental-rate/list:
    post:
      operationId: rentalRateList
      summary: List rental rates
      x-route-class: Tier A
      x-qps-target: 200
      x-concurrency-target: 200
      x-latency-p95-ms: 200
      parameters: [ { $ref: '#/components/parameters/OrgHeader' }, { $ref: '#/components/parameters/LogicalHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/RentalRateListRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/RentalRateListEnvelope' }
  /rental-rate/status/set:
    post:
      operationId: rentalRateStatusSet
      summary: Update rental rate status
      x-route-class: Tier A
      x-qps-target: 50
      x-concurrency-target: 200
      x-latency-p95-ms: 500
      parameters: [ { $ref: '#/components/parameters/OrgHeader' }, { $ref: '#/components/parameters/LogicalHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/RentalRateStatusSetRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/RentalRateEnvelope' }
  /fx/rate/set:
    post:
      operationId: fxRateSet
      summary: Create or update an FX rate
      x-route-class: Tier A
      x-qps-target: 50
      x-concurrency-target: 200
      x-latency-p95-ms: 500
      parameters: [ { $ref: '#/components/parameters/OrgHeader' }, { $ref: '#/components/parameters/LogicalHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/FxRateSetRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/FxRateEnvelope' }
  /fx/rate/get:
    post:
      operationId: fxRateGet
      summary: Get an FX rate by ID or currency pair
      x-route-class: Tier A
      x-qps-target: 200
      x-concurrency-target: 400
      x-latency-p95-ms: 200
      parameters: [ { $ref: '#/components/parameters/OrgHeader' }, { $ref: '#/components/parameters/LogicalHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/FxRateGetRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/FxRateEnvelope' }
  /fx/rate/list:
    post:
      operationId: fxRateList
      summary: List FX rates with optional currency filters
      x-route-class: Tier A
      x-qps-target: 200
      x-concurrency-target: 400
      x-latency-p95-ms: 200
      parameters: [ { $ref: '#/components/parameters/OrgHeader' }, { $ref: '#/components/parameters/LogicalHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema: { $ref: '#/components/schemas/FxRateListRequest' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/FxRateListEnvelope' }
  /installment-plan/set:
    post:
      operationId: installmentPlanSet
      summary: Create or update an installment/layaway plan
      x-route-class: Tier A
      x-qps-target: 100
      x-concurrency-target: 200
      x-latency-p95-ms: 300
      parameters: [ { $ref: '#/components/parameters/OrgHeader' }, { $ref: '#/components/parameters/LogicalHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              x-idempotency-scope: orgcode+route+idempotency_key
              x-idempotency-retention-hours: 24
              x-idempotency-replay: return_original_response
              required: [installment_plan, reason, source_refs]
              properties:
                installment_plan:
                  type: object
                  required: [installment_count, installment_interval_days, currency]
                  properties:
                    plan_id: { type: string }
                    code: { type: string }
                    caption: { type: string }
                    status: { type: string, enum: [draft, active, suspended, archived, doomed] }
                    installment_count: { type: integer, minimum: 2 }
                    installment_interval_days: { type: integer, minimum: 1 }
                    down_payment_percent: { type: number, minimum: 0, maximum: 100 }
                    down_payment_fixed_minor: { type: integer, minimum: 0 }
                    interest_rate_bps: { type: integer, minimum: 0 }
                    currency: { type: string, minLength: 3, maxLength: 3 }
                reason: { type: string }
                source_refs: { type: array, items: { type: object } }
                idempotency_key: { type: string }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/Envelope' }
  /installment-plan/get:
    post:
      operationId: installmentPlanGet
      summary: Fetch an installment plan by ID
      x-route-class: Tier A
      x-qps-target: 500
      x-concurrency-target: 400
      x-latency-p95-ms: 200
      parameters: [ { $ref: '#/components/parameters/OrgHeader' }, { $ref: '#/components/parameters/LogicalHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required: [plan_id]
              properties:
                plan_id: { type: string }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/Envelope' }
  /installment-plan/list:
    post:
      operationId: installmentPlanList
      summary: List installment plans with optional status filter
      x-route-class: Tier A
      x-qps-target: 500
      x-concurrency-target: 400
      x-latency-p95-ms: 200
      parameters: [ { $ref: '#/components/parameters/OrgHeader' }, { $ref: '#/components/parameters/LogicalHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              properties:
                status: { type: string, enum: [draft, active, suspended, archived, doomed] }
                limit: { type: integer, minimum: 1, maximum: 256, default: 50 }
                next_token: { type: object }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/Envelope' }
  /installment-plan/status/set:
    post:
      operationId: installmentPlanStatusSet
      summary: Update installment plan status
      x-route-class: Tier A
      x-qps-target: 100
      x-concurrency-target: 200
      x-latency-p95-ms: 300
      parameters: [ { $ref: '#/components/parameters/OrgHeader' }, { $ref: '#/components/parameters/LogicalHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required: [plan_id, status, reason, source_refs]
              properties:
                plan_id: { type: string }
                status: { type: string, enum: [draft, active, suspended, archived, doomed] }
                expected_revision: { type: integer }
                reason: { type: string }
                source_refs: { type: array, items: { type: object } }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/Envelope' }
  /trade-agreement/set:
    post:
      operationId: tradeAgreementSet
      summary: Create or update a trade agreement
      x-route-class: Tier A
      x-qps-target: 100
      x-concurrency-target: 200
      x-latency-p95-ms: 300
      parameters: [ { $ref: '#/components/parameters/OrgHeader' }, { $ref: '#/components/parameters/LogicalHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              x-idempotency-scope: orgcode+route+idempotency_key
              x-idempotency-retention-hours: 24
              x-idempotency-replay: return_original_response
              required: [trade_agreement, reason, source_refs]
              properties:
                trade_agreement:
                  type: object
                  required: [agreement_type, code, effective_from]
                  properties:
                    agreement_id: { type: string }
                    code: { type: string }
                    caption: { type: string }
                    status: { type: string, enum: [draft, active, suspended, archived, doomed] }
                    agreement_type: { type: string, enum: [fta, gsp, preferential, bilateral, unilateral] }
                    origin_country: { type: string, minLength: 2, maxLength: 2 }
                    destination_country: { type: string, minLength: 2, maxLength: 2 }
                    hs_code_prefixes: { type: array, items: { type: string } }
                    duty_rate_bps: { type: integer, minimum: 0 }
                    effective_from: { type: string, format: date }
                    effective_to: { type: string, format: date }
                    certification_required: { type: boolean }
                    rules_of_origin_summary: { type: string }
                reason: { type: string }
                source_refs: { type: array, items: { type: object } }
                idempotency_key: { type: string }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/Envelope' }
  /trade-agreement/get:
    post:
      operationId: tradeAgreementGet
      summary: Fetch a trade agreement by ID
      x-route-class: Tier A
      x-qps-target: 500
      x-concurrency-target: 400
      x-latency-p95-ms: 200
      parameters: [ { $ref: '#/components/parameters/OrgHeader' }, { $ref: '#/components/parameters/LogicalHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required: [agreement_id]
              properties:
                agreement_id: { type: string }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/Envelope' }
  /trade-agreement/list:
    post:
      operationId: tradeAgreementList
      summary: List trade agreements with optional status filter
      x-route-class: Tier A
      x-qps-target: 500
      x-concurrency-target: 400
      x-latency-p95-ms: 200
      parameters: [ { $ref: '#/components/parameters/OrgHeader' }, { $ref: '#/components/parameters/LogicalHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              properties:
                status: { type: string, enum: [draft, active, suspended, archived, doomed] }
                limit: { type: integer, minimum: 1, maximum: 256, default: 50 }
                next_token: { type: object }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/Envelope' }
  /trade-agreement/status/set:
    post:
      operationId: tradeAgreementStatusSet
      summary: Update trade agreement status
      x-route-class: Tier A
      x-qps-target: 100
      x-concurrency-target: 200
      x-latency-p95-ms: 300
      parameters: [ { $ref: '#/components/parameters/OrgHeader' }, { $ref: '#/components/parameters/LogicalHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required: [agreement_id, status, reason, source_refs]
              properties:
                agreement_id: { type: string }
                status: { type: string, enum: [draft, active, suspended, archived, doomed] }
                expected_revision: { type: integer }
                reason: { type: string }
                source_refs: { type: array, items: { type: object } }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/Envelope' }
  /commission-rule/set:
    post:
      operationId: commissionRuleSet
      summary: Create or update a commission rule
      x-status: draft
      x-route-class: Tier A
      x-qps-target: 100
      x-concurrency-target: 200
      x-latency-p95-ms: 300
      x-idempotent: true
      parameters: [ { $ref: '#/components/parameters/OrgHeader' }, { $ref: '#/components/parameters/LogicalHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              x-idempotency-scope: orgcode+route+idempotency_key
              x-idempotency-retention-hours: 24
              x-idempotency-replay: return_original_response
              required: [commission_rule, reason, source_refs]
              properties:
                commission_rule:
                  type: object
                  required: [rule_type]
                  properties:
                    rule_id: { type: string }
                    code: { type: string }
                    caption: { type: string }
                    status: { type: string, enum: [draft, active, suspended, archived, doomed] }
                    rule_type: { type: string, enum: [percentage, flat_amount, tiered] }
                    rate_bps: { type: integer, minimum: 0, maximum: 10000 }
                    flat_amount_minor: { type: integer }
                    tiers: { type: array, items: { type: object, properties: { min_amount_minor: { type: integer }, max_amount_minor: { type: integer }, rate_bps: { type: integer } } } }
                    currency: { type: string }
                    scope: { oneOf: [{ type: string, const: all }, { type: object, properties: { channel_codes: { type: array, items: { type: string } }, category_ids: { type: array, items: { type: string } }, product_types: { type: array, items: { type: string } } } }] }
                    effective_from: { type: string, format: date-time }
                    effective_to: { type: string, format: date-time }
                reason: { type: string }
                source_refs: { type: array, items: { type: object } }
                idempotency_key: { type: string }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/Envelope' }
  /commission-rule/get:
    post:
      operationId: commissionRuleGet
      summary: Get commission rule by rule_id
      x-status: draft
      x-route-class: Tier A
      x-qps-target: 500
      x-concurrency-target: 400
      x-latency-p95-ms: 200
      parameters: [ { $ref: '#/components/parameters/OrgHeader' }, { $ref: '#/components/parameters/LogicalHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required: [rule_id]
              properties:
                rule_id: { type: string }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/Envelope' }
  /commission-rule/list:
    post:
      operationId: commissionRuleList
      summary: List commission rules with optional status filter
      x-status: draft
      x-route-class: Tier A
      x-qps-target: 500
      x-concurrency-target: 400
      x-latency-p95-ms: 200
      parameters: [ { $ref: '#/components/parameters/OrgHeader' }, { $ref: '#/components/parameters/LogicalHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              properties:
                status: { type: string, enum: [draft, active, suspended, archived, doomed] }
                limit: { type: integer, minimum: 1, maximum: 256, default: 50 }
                next_token: { type: object }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/Envelope' }
  /commission-rule/status/set:
    post:
      operationId: commissionRuleStatusSet
      summary: Update commission rule status
      x-status: draft
      x-route-class: Tier A
      x-qps-target: 100
      x-concurrency-target: 200
      x-latency-p95-ms: 300
      parameters: [ { $ref: '#/components/parameters/OrgHeader' }, { $ref: '#/components/parameters/LogicalHeader' } ]
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required: [rule_id, status, reason, source_refs]
              properties:
                rule_id: { type: string }
                status: { type: string, enum: [draft, active, suspended, archived, doomed] }
                expected_revision: { type: integer }
                reason: { type: string }
                source_refs: { type: array, items: { type: object } }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/Envelope' }
  # --- Coupon Codes (G97) ---
  /coupon/create:
    post:
      summary: Create a coupon code
      tags: [Coupon]
      x-status: draft
      x-route-class: write
      x-qps-target: 20
      x-concurrency-target: 5
      x-latency-p95-ms: 300
      security:
        - BearerAuth: []
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required: [code]
              properties:
                code: { type: string }
                promotion_id: { type: string }
                max_uses: { type: integer }
                max_uses_per_customer: { type: integer }
                valid_from: { type: string, format: date-time }
                valid_to: { type: string, format: date-time }
                customer_scope: { description: '"all" or array of customer_refs' }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/Envelope' }
  /coupon/get:
    post:
      summary: Get a coupon code by code
      tags: [Coupon]
      x-status: draft
      x-route-class: read
      x-qps-target: 50
      x-concurrency-target: 10
      x-latency-p95-ms: 200
      security:
        - BearerAuth: []
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required: [code]
              properties:
                code: { type: string }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/Envelope' }
  /coupon/list:
    post:
      summary: List coupon codes
      tags: [Coupon]
      x-status: draft
      x-route-class: read
      x-qps-target: 50
      x-concurrency-target: 10
      x-latency-p95-ms: 200
      security:
        - BearerAuth: []
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              properties:
                limit: { type: integer }
                next_token: { type: string }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/Envelope' }
  /coupon/validate:
    post:
      summary: Validate a coupon code without redeeming
      tags: [Coupon]
      x-status: draft
      x-route-class: read
      x-qps-target: 100
      x-concurrency-target: 20
      x-latency-p95-ms: 200
      security:
        - BearerAuth: []
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required: [code]
              properties:
                code: { type: string }
                customer_ref: { type: string }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/Envelope' }
  /coupon/redeem:
    post:
      summary: Redeem a coupon code
      tags: [Coupon]
      x-status: draft
      x-route-class: write
      x-qps-target: 50
      x-concurrency-target: 10
      x-latency-p95-ms: 300
      security:
        - BearerAuth: []
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required: [code, customer_ref]
              properties:
                code: { type: string }
                customer_ref: { type: string }
                order_ref: { type: string }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/Envelope' }
  /coupon/status/set:
    post:
      summary: Set coupon code status
      tags: [Coupon]
      x-status: draft
      x-route-class: write
      x-qps-target: 20
      x-concurrency-target: 5
      x-latency-p95-ms: 300
      security:
        - BearerAuth: []
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required: [code, status, reason, source_refs]
              properties:
                code: { type: string }
                status: { type: string, enum: [active, inactive, expired] }
                expected_revision: { type: integer }
                reason: { type: string }
                source_refs: { type: array, items: { type: object } }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/Envelope' }
  /subscription-instance/create:
    post:
      summary: Create subscription instance (L4)
      tags: [SubscriptionInstance]
      x-status: draft
      x-route-class: write
      x-qps-target: 20
      x-concurrency-target: 5
      x-latency-p95-ms: 300
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required: [subscription_instance, reason, source_refs]
              properties:
                subscription_instance: { type: object }
                reason: { type: string }
                source_refs: { type: array, items: { type: object } }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/Envelope' }
  /subscription-instance/get:
    post:
      summary: Get subscription instance (L4)
      tags: [SubscriptionInstance]
      x-status: draft
      x-route-class: read
      x-qps-target: 50
      x-concurrency-target: 10
      x-latency-p95-ms: 100
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required: [instance_id]
              properties:
                instance_id: { type: string }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/Envelope' }
  /subscription-instance/list:
    post:
      summary: List subscription instances (L4)
      tags: [SubscriptionInstance]
      x-status: draft
      x-route-class: read
      x-qps-target: 50
      x-concurrency-target: 10
      x-latency-p95-ms: 200
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              properties:
                status: { type: string }
                customer_guid: { type: string }
                limit: { type: integer }
                next_token: { type: string }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/Envelope' }
  /subscription-instance/cancel:
    post:
      summary: Cancel subscription instance (L4)
      tags: [SubscriptionInstance]
      x-status: draft
      x-route-class: write
      x-qps-target: 20
      x-concurrency-target: 5
      x-latency-p95-ms: 300
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required: [instance_id, reason, source_refs]
              properties:
                instance_id: { type: string }
                reason: { type: string }
                source_refs: { type: array, items: { type: object } }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/Envelope' }
  /subscription-instance/pause:
    post:
      summary: Pause subscription instance (L4)
      tags: [SubscriptionInstance]
      x-status: draft
      x-route-class: write
      x-qps-target: 20
      x-concurrency-target: 5
      x-latency-p95-ms: 300
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required: [instance_id, reason, source_refs]
              properties:
                instance_id: { type: string }
                reason: { type: string }
                source_refs: { type: array, items: { type: object } }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/Envelope' }
  /subscription-instance/resume:
    post:
      summary: Resume subscription instance (L4)
      tags: [SubscriptionInstance]
      x-status: draft
      x-route-class: write
      x-qps-target: 20
      x-concurrency-target: 5
      x-latency-p95-ms: 300
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required: [instance_id, reason, source_refs]
              properties:
                instance_id: { type: string }
                reason: { type: string }
                source_refs: { type: array, items: { type: object } }
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema: { $ref: '#/components/schemas/Envelope' }
