{
  "openapi": "3.1.0",
  "info": {
    "title": "AeroCell: Affordable eSIMs \u2014 Read-only API",
    "version": "0.4.0",
    "description": "Live country and multi-country travel eSIM searches by Mezsondra LTD. Public and credential-free. Shared business logic with https://aerocell.app/mcp (Streamable HTTP). Purchases remain on aerocell.app via returned checkout links. No order or payment endpoints. Unknown and repeated query parameters are rejected. Complete comparison catalog with stable identities, every purchasable day-pass duration, explicit allowance behavior and conditional HTTP reads.",
    "termsOfService": "https://aerocell.app/terms",
    "contact": {
      "name": "Mezsondra LTD \u2014 AeroCell Support",
      "url": "https://aerocell.app/support",
      "email": "support@aerocell.app"
    }
  },
  "servers": [
    {
      "url": "https://aerocell.app"
    }
  ],
  "security": [],
  "externalDocs": {
    "description": "Developer guide, MCP tools and integration examples",
    "url": "https://aerocell.app/developers"
  },
  "paths": {
    "/api/v1/esim/plans": {
      "get": {
        "operationId": "findEsimPlans",
        "summary": "Find plans for one country",
        "tags": [
          "eSIM plans"
        ],
        "parameters": [
          {
            "name": "country_code",
            "in": "query",
            "required": true,
            "schema": {
              "type": "string",
              "pattern": "^[A-Za-z]{2}$",
              "description": "Assigned ISO alpha-2 code; catalog-supported XK is also accepted. Codes are case-insensitive."
            },
            "description": "Required destination country.",
            "example": "JP"
          },
          {
            "name": "start_date",
            "in": "query",
            "required": false,
            "schema": {
              "type": "string",
              "format": "date"
            },
            "description": "Provide with end_date. Dates constrain validity only, not future inventory or scheduled activation.",
            "example": "2026-10-15"
          },
          {
            "name": "end_date",
            "in": "query",
            "required": false,
            "schema": {
              "type": "string",
              "format": "date"
            },
            "description": "Inclusive trip end. Range must be ordered and 1\u2013366 days.",
            "example": "2026-10-25"
          },
          {
            "name": "min_data_gb",
            "in": "query",
            "required": false,
            "schema": {
              "type": "number",
              "minimum": 0
            },
            "description": "Minimum data allowance in GB.",
            "example": 3
          },
          {
            "name": "max_price_usd",
            "in": "query",
            "required": false,
            "schema": {
              "type": "number",
              "exclusiveMinimum": 0
            },
            "description": "Maximum plan price in USD.",
            "example": 25
          },
          {
            "name": "require_trip_coverage",
            "in": "query",
            "required": false,
            "schema": {
              "type": "boolean",
              "default": true
            },
            "description": "With dates, omit shorter-validity plans unless false. Use literal true or false.",
            "example": true
          },
          {
            "name": "limit",
            "in": "query",
            "required": false,
            "schema": {
              "type": "integer",
              "minimum": 1,
              "maximum": 20,
              "default": 8
            },
            "description": "Maximum returned plans, cheapest first; total_matching is before limiting.",
            "example": 8
          }
        ],
        "responses": {
          "200": {
            "description": "Current result. Sample prices and IDs are illustrative fixtures, not live offers. Empty searches return plans: [] and total_matching: 0.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/CountrySearch"
                },
                "examples": {
                  "illustrative": {
                    "summary": "Illustrative response only",
                    "value": {
                      "country": {
                        "code": "JP",
                        "name": "Japan"
                      },
                      "trip_days": 11,
                      "currency": "USD",
                      "updated_at": "2026-10-12T12:00:00Z",
                      "total_matching": 1,
                      "browse_url": "https://aerocell.app/plans",
                      "note": "Illustrative fixture only. Fetch live prices and real plan IDs before recommending or opening checkout.",
                      "plans": [
                        {
                          "id": "EXAMPLE-JP-5GB",
                          "name": "Example Japan 5 GB",
                          "data_gb": 5,
                          "validity_days": 15,
                          "price_usd": 9,
                          "network": "5G",
                          "operators": [
                            "Example operator"
                          ],
                          "covers_trip": true,
                          "plan_page_url": "https://aerocell.app/plans/japan",
                          "checkout_url": "https://aerocell.app/checkout/EXAMPLE-JP-5GB"
                        }
                      ]
                    }
                  },
                  "noMatches": {
                    "summary": "No matching plans",
                    "value": {
                      "country": {
                        "code": "JP",
                        "name": "Japan"
                      },
                      "trip_days": 11,
                      "currency": "USD",
                      "updated_at": "2026-10-12T12:00:00Z",
                      "total_matching": 0,
                      "browse_url": "https://aerocell.app/plans",
                      "note": "Illustrative fixture only. Fetch live prices and real plan IDs before recommending or opening checkout.",
                      "plans": []
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Missing, unknown, repeated or invalid parameters; invalid dates or country codes.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "error": {
                    "code": "invalid_input",
                    "message": "Provide both start_date and end_date."
                  }
                }
              }
            }
          },
          "405": {
            "description": "Read-only endpoint; use GET.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "error": {
                    "code": "method_not_allowed",
                    "message": "This read-only endpoint supports GET."
                  }
                }
              }
            }
          },
          "502": {
            "description": "Invalid response from the upstream catalog.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "error": {
                    "code": "invalid_catalog_response",
                    "message": "AeroCell returned an invalid plan response."
                  }
                }
              }
            }
          },
          "503": {
            "description": "Catalog temporarily unavailable; retry later.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "error": {
                    "code": "catalog_unavailable",
                    "message": "AeroCell plans are temporarily unavailable. Please try again later."
                  }
                }
              }
            },
            "headers": {
              "Retry-After": {
                "schema": {
                  "type": "integer"
                },
                "description": "Suggested retry delay in seconds.",
                "example": 30
              }
            }
          }
        }
      }
    },
    "/api/v1/esim/plans/{plan_id}": {
      "get": {
        "operationId": "getEsimPlan",
        "summary": "Refresh a country plan; requires its country code",
        "tags": [
          "eSIM plans"
        ],
        "parameters": [
          {
            "name": "plan_id",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string",
              "pattern": "^[A-Za-z0-9_-]{1,100}$"
            },
            "description": "Use an actual ID from country search. Regional IDs cannot be retrieved here."
          },
          {
            "name": "country_code",
            "in": "query",
            "required": true,
            "schema": {
              "type": "string",
              "pattern": "^[A-Za-z]{2}$",
              "description": "Assigned ISO alpha-2 code; catalog-supported XK is also accepted. Codes are case-insensitive."
            },
            "description": "Required: same country_code used to find the plan.",
            "example": "JP"
          }
        ],
        "responses": {
          "200": {
            "description": "Current result. Sample prices and IDs are illustrative fixtures, not live offers. Empty searches return plans: [] and total_matching: 0.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PlanDetail"
                },
                "examples": {
                  "illustrative": {
                    "summary": "Illustrative response only",
                    "value": {
                      "country": {
                        "code": "JP",
                        "name": "Japan"
                      },
                      "currency": "USD",
                      "updated_at": "2026-10-12T12:00:00Z",
                      "plan": {
                        "id": "EXAMPLE-JP-5GB",
                        "name": "Example Japan 5 GB",
                        "data_gb": 5,
                        "validity_days": 15,
                        "price_usd": 9,
                        "network": "5G",
                        "operators": [
                          "Example operator"
                        ],
                        "covers_trip": null,
                        "plan_page_url": "https://aerocell.app/plans/japan",
                        "checkout_url": "https://aerocell.app/checkout/EXAMPLE-JP-5GB"
                      },
                      "note": "Illustrative fixture only. Fetch live prices and real plan IDs before recommending or opening checkout."
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Missing, unknown, repeated or invalid parameters; invalid dates or country codes.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "error": {
                    "code": "invalid_input",
                    "message": "Provide both start_date and end_date."
                  }
                }
              }
            }
          },
          "404": {
            "description": "Plan not available in the supplied country. Regional IDs are not supported by this detail route.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "error": {
                    "code": "plan_not_found",
                    "message": "That plan is not currently available for this country."
                  }
                }
              }
            }
          },
          "405": {
            "description": "Read-only endpoint; use GET.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "error": {
                    "code": "method_not_allowed",
                    "message": "This read-only endpoint supports GET."
                  }
                }
              }
            }
          },
          "502": {
            "description": "Invalid response from the upstream catalog.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "error": {
                    "code": "invalid_catalog_response",
                    "message": "AeroCell returned an invalid plan response."
                  }
                }
              }
            }
          },
          "503": {
            "description": "Catalog temporarily unavailable; retry later.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "error": {
                    "code": "catalog_unavailable",
                    "message": "AeroCell plans are temporarily unavailable. Please try again later."
                  }
                }
              }
            },
            "headers": {
              "Retry-After": {
                "schema": {
                  "type": "integer"
                },
                "description": "Suggested retry delay in seconds.",
                "example": 30
              }
            }
          }
        }
      }
    },
    "/api/v1/esim/regional-plans": {
      "get": {
        "operationId": "findRegionalEsimPlans",
        "summary": "Find bundles covering every itinerary country",
        "tags": [
          "eSIM plans"
        ],
        "parameters": [
          {
            "name": "country_codes",
            "in": "query",
            "required": false,
            "schema": {
              "type": "array",
              "minItems": 1,
              "maxItems": 30,
              "uniqueItems": true,
              "items": {
                "type": "string",
                "pattern": "^[A-Za-z]{2}$",
                "description": "Assigned ISO alpha-2 code; catalog-supported XK is also accepted. Codes are case-insensitive."
              }
            },
            "description": "Comma-separated distinct codes. Required unless region is given. Every code must be in the returned bundle's exact coverage list.",
            "example": [
              "FR",
              "IT",
              "ES"
            ],
            "style": "form",
            "explode": false
          },
          {
            "name": "region",
            "in": "query",
            "required": false,
            "schema": {
              "type": "string",
              "enum": [
                "global",
                "europe",
                "asia_pacific",
                "southeast_asia",
                "latin_america",
                "middle_east_north_africa",
                "gulf"
              ]
            },
            "description": "Required unless country_codes is given. Can combine both filters. Region-only results still require coverage review.",
            "example": "europe"
          },
          {
            "name": "start_date",
            "in": "query",
            "required": false,
            "schema": {
              "type": "string",
              "format": "date"
            },
            "description": "Provide with end_date. Dates constrain validity only, not future inventory or scheduled activation.",
            "example": "2026-10-15"
          },
          {
            "name": "end_date",
            "in": "query",
            "required": false,
            "schema": {
              "type": "string",
              "format": "date"
            },
            "description": "Inclusive trip end. Range must be ordered and 1\u2013366 days.",
            "example": "2026-10-25"
          },
          {
            "name": "min_data_gb",
            "in": "query",
            "required": false,
            "schema": {
              "type": "number",
              "minimum": 0
            },
            "description": "Minimum data allowance in GB.",
            "example": 3
          },
          {
            "name": "max_price_usd",
            "in": "query",
            "required": false,
            "schema": {
              "type": "number",
              "exclusiveMinimum": 0
            },
            "description": "Maximum plan price in USD.",
            "example": 25
          },
          {
            "name": "require_trip_coverage",
            "in": "query",
            "required": false,
            "schema": {
              "type": "boolean",
              "default": true
            },
            "description": "With dates, omit shorter-validity plans unless false. Use literal true or false.",
            "example": true
          },
          {
            "name": "limit",
            "in": "query",
            "required": false,
            "schema": {
              "type": "integer",
              "minimum": 1,
              "maximum": 20,
              "default": 8
            },
            "description": "Maximum returned plans, cheapest first; total_matching is before limiting.",
            "example": 8
          }
        ],
        "responses": {
          "200": {
            "description": "Current result. Sample prices and IDs are illustrative fixtures, not live offers. Empty searches return plans: [] and total_matching: 0.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/RegionalSearch"
                },
                "examples": {
                  "illustrative": {
                    "summary": "Illustrative response only",
                    "value": {
                      "requested_country_codes": [
                        "FR",
                        "IT",
                        "ES"
                      ],
                      "region": "europe",
                      "trip_days": 11,
                      "currency": "USD",
                      "updated_at": "2026-10-12T12:00:00Z",
                      "total_matching": 1,
                      "browse_url": "https://aerocell.app/plans",
                      "note": "Illustrative fixture only. Fetch live prices and real plan IDs before recommending or opening checkout.",
                      "plans": [
                        {
                          "id": "EXAMPLE-EU-5GB",
                          "name": "Example Europe 5 GB",
                          "data_gb": 5,
                          "validity_days": 15,
                          "price_usd": 9,
                          "network": "5G",
                          "operators": [
                            "Example operator"
                          ],
                          "covers_trip": true,
                          "plan_page_url": "https://aerocell.app/plans/europe",
                          "checkout_url": "https://aerocell.app/checkout/EXAMPLE-EU-5GB",
                          "region_code": "EU-3",
                          "country_codes": [
                            "FR",
                            "IT",
                            "ES"
                          ],
                          "country_count": 3
                        }
                      ]
                    }
                  },
                  "noMatches": {
                    "summary": "No matching plans",
                    "value": {
                      "requested_country_codes": [
                        "FR",
                        "IT",
                        "ES"
                      ],
                      "region": "europe",
                      "trip_days": 11,
                      "currency": "USD",
                      "updated_at": "2026-10-12T12:00:00Z",
                      "total_matching": 0,
                      "browse_url": "https://aerocell.app/plans",
                      "note": "Illustrative fixture only. Fetch live prices and real plan IDs before recommending or opening checkout.",
                      "plans": []
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Missing, unknown, repeated or invalid parameters; invalid dates or country codes.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "error": {
                    "code": "invalid_input",
                    "message": "Provide both start_date and end_date."
                  }
                }
              }
            }
          },
          "405": {
            "description": "Read-only endpoint; use GET.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "error": {
                    "code": "method_not_allowed",
                    "message": "This read-only endpoint supports GET."
                  }
                }
              }
            }
          },
          "502": {
            "description": "Invalid response from the upstream catalog.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "error": {
                    "code": "invalid_catalog_response",
                    "message": "AeroCell returned an invalid plan response."
                  }
                }
              }
            }
          },
          "503": {
            "description": "Catalog temporarily unavailable; retry later.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                },
                "example": {
                  "error": {
                    "code": "catalog_unavailable",
                    "message": "AeroCell plans are temporarily unavailable. Please try again later."
                  }
                }
              }
            },
            "headers": {
              "Retry-After": {
                "schema": {
                  "type": "integer"
                },
                "description": "Suggested retry delay in seconds.",
                "example": 30
              }
            }
          }
        }
      }
    },
    "/api/v1/esim/catalog": {
      "get": {
        "operationId": "getComparisonCatalog",
        "summary": "Import the complete purchasable AeroCell comparison catalog",
        "tags": [
          "eSIM plans"
        ],
        "description": "Public, credential-free feed. No query parameters, pagination or search limit. Includes all plans accepted by checkout and all 1\u201390-day variants. Hidden products and customer-only top-ups are excluded. The fixed-plan storefront minimum (1,000,000,000 bytes) is preserved; sub-1GB daily allowances are included. Poll every 15 minutes; send If-None-Match. Snapshot rebuilds every five minutes; provider source age is limited to 15 minutes. Browser CORS allows all origins without credentials. GET, HEAD and OPTIONS are supported.",
        "parameters": [
          {
            "name": "If-None-Match",
            "in": "header",
            "required": false,
            "schema": {
              "type": "string"
            },
            "description": "ETag from the previous successful download."
          }
        ],
        "responses": {
          "200": {
            "description": "Complete validated snapshot. Illustrative example only.",
            "headers": {
              "ETag": {
                "schema": {
                  "type": "string"
                },
                "description": "Opaque HTTP validator; send this value as If-None-Match on the next request."
              },
              "Cache-Control": {
                "schema": {
                  "type": "string"
                },
                "description": "public, no-cache: stored responses must be revalidated."
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ComparisonCatalog"
                },
                "examples": {
                  "illustrative": {
                    "summary": "Illustrative fixture, not a live offer",
                    "value": {
                      "schema_version": 1,
                      "provider": "AeroCell",
                      "currency": "USD",
                      "price_basis": "Retail before coupons; daily variants show the total duration price.",
                      "total_plans": 1,
                      "plans": [
                        {
                          "id": "EXAMPLE-JP-5GB",
                          "package_code": "EXAMPLE-JP-5GB",
                          "name": "Illustrative Japan 5GB (not a live offer)",
                          "country_codes": [
                            "JP"
                          ],
                          "data_gb": 5,
                          "allowance_period": "plan",
                          "is_unlimited": false,
                          "allowance_behavior": "total",
                          "reduced_speed_kbps": null,
                          "maximum_speed_kbps": null,
                          "validity_days": 15,
                          "is_daily": false,
                          "price_usd": 9,
                          "operators": [
                            {
                              "name": "Example operator",
                              "network": "5G"
                            }
                          ],
                          "plan_page_url": "https://aerocell.app/plans/japan",
                          "checkout_url": "https://aerocell.app/checkout/EXAMPLE-JP-5GB"
                        }
                      ],
                      "catalog_version": "3cedf68183c3a264aa809b94f0ffa23cd572c44831a56586e612918c4df24dc4",
                      "generated_at": "2026-10-13T00:00:00.000Z",
                      "source_updated_at": "2026-10-13T00:00:00.000Z",
                      "refresh_after_seconds": 900
                    }
                  }
                }
              }
            }
          },
          "304": {
            "description": "Unchanged, successfully revalidated snapshot; no response body.",
            "headers": {
              "ETag": {
                "schema": {
                  "type": "string"
                },
                "description": "Opaque HTTP validator; send this value as If-None-Match on the next request."
              },
              "Cache-Control": {
                "schema": {
                  "type": "string"
                },
                "description": "public, no-cache: stored responses must be revalidated."
              }
            }
          },
          "400": {
            "description": "Query parameters are not supported.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          },
          "405": {
            "description": "Read-only catalog; use GET, HEAD or OPTIONS.",
            "headers": {
              "Allow": {
                "schema": {
                  "type": "string"
                }
              }
            }
          },
          "429": {
            "description": "Catalog rate limit exceeded (300 requests per 15 minutes per IP, shared with other Express catalog routes). Respect Retry-After.",
            "headers": {
              "Retry-After": {
                "schema": {
                  "type": "integer"
                }
              }
            }
          },
          "503": {
            "description": "Complete catalog unavailable or required plan metadata not verified. Keep your previous import and retry; never treat this as an empty catalog.",
            "headers": {
              "Retry-After": {
                "schema": {
                  "type": "integer"
                },
                "example": 30
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Error"
                }
              }
            }
          }
        }
      }
    },
    "/api/partners/comparison-catalog": {
      "get": {
        "operationId": "getPartnerComparisonCatalog",
        "summary": "Import the complete catalog with registered partner links",
        "tags": [
          "eSIM plans"
        ],
        "security": [
          {
            "partnerFeedKey": []
          }
        ],
        "description": "Same plans as the public comparison catalog with partner purchase links when configured. Server-side use only; Cache-Control: no-store. No query parameters. Requires an existing active, agreed partner within its campaign dates and the enabled affiliate program. Does not create credentials or activate a campaign.",
        "responses": {
          "200": {
            "description": "Complete partner catalog; prices are unchanged.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PartnerComparisonCatalog"
                }
              }
            }
          },
          "400": {
            "description": "Query parameters are not supported."
          },
          "401": {
            "description": "Missing or malformed feed credential."
          },
          "403": {
            "description": "Credential revoked, partner unavailable or affiliate program disabled."
          },
          "429": {
            "description": "Shared catalog rate limit exceeded. Respect Retry-After."
          },
          "503": {
            "description": "Complete catalog temporarily unavailable. Retain your previous import and retry.",
            "headers": {
              "Retry-After": {
                "schema": {
                  "type": "integer"
                },
                "example": 30
              }
            }
          }
        }
      }
    }
  },
  "components": {
    "schemas": {
      "Country": {
        "type": "object",
        "required": [
          "code",
          "name"
        ],
        "properties": {
          "code": {
            "type": "string",
            "pattern": "^[A-Za-z]{2}$",
            "description": "Assigned ISO alpha-2 code; catalog-supported XK is also accepted. Codes are case-insensitive."
          },
          "name": {
            "type": "string"
          }
        },
        "additionalProperties": false
      },
      "Plan": {
        "type": "object",
        "required": [
          "id",
          "name",
          "data_gb",
          "validity_days",
          "price_usd",
          "network",
          "operators",
          "covers_trip",
          "plan_page_url",
          "checkout_url"
        ],
        "properties": {
          "id": {
            "type": "string",
            "pattern": "^[A-Za-z0-9_-]{1,100}$"
          },
          "name": {
            "type": "string"
          },
          "data_gb": {
            "type": "number",
            "minimum": 0,
            "description": "Displayed GB rounded to one decimal; 1 GB = 1024^3 bytes."
          },
          "validity_days": {
            "type": "number",
            "exclusiveMinimum": 0
          },
          "price_usd": {
            "type": "number",
            "minimum": 0
          },
          "network": {
            "type": "string"
          },
          "operators": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Catalog operator summary, up to four names; not a complete per-country network map."
          },
          "covers_trip": {
            "type": [
              "boolean",
              "null"
            ]
          },
          "plan_page_url": {
            "type": "string",
            "format": "uri"
          },
          "checkout_url": {
            "type": "string",
            "format": "uri"
          }
        },
        "additionalProperties": false
      },
      "RegionalPlan": {
        "type": "object",
        "required": [
          "id",
          "name",
          "data_gb",
          "validity_days",
          "price_usd",
          "network",
          "operators",
          "covers_trip",
          "plan_page_url",
          "checkout_url",
          "region_code",
          "country_codes",
          "country_count"
        ],
        "properties": {
          "id": {
            "type": "string",
            "pattern": "^[A-Za-z0-9_-]{1,100}$"
          },
          "name": {
            "type": "string"
          },
          "data_gb": {
            "type": "number",
            "minimum": 0,
            "description": "Displayed GB rounded to one decimal; 1 GB = 1024^3 bytes."
          },
          "validity_days": {
            "type": "number",
            "exclusiveMinimum": 0
          },
          "price_usd": {
            "type": "number",
            "minimum": 0
          },
          "network": {
            "type": "string"
          },
          "operators": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Catalog operator summary, up to four names; not a complete per-country network map."
          },
          "covers_trip": {
            "type": [
              "boolean",
              "null"
            ]
          },
          "plan_page_url": {
            "type": "string",
            "format": "uri"
          },
          "checkout_url": {
            "type": "string",
            "format": "uri"
          },
          "region_code": {
            "type": "string"
          },
          "country_codes": {
            "type": "array",
            "minItems": 2,
            "uniqueItems": true,
            "items": {
              "type": "string",
              "pattern": "^[A-Za-z]{2}$",
              "description": "Assigned ISO alpha-2 code; catalog-supported XK is also accepted. Codes are case-insensitive."
            }
          },
          "country_count": {
            "type": "integer",
            "minimum": 2
          }
        },
        "additionalProperties": false
      },
      "CountrySearch": {
        "type": "object",
        "required": [
          "country",
          "trip_days",
          "currency",
          "updated_at",
          "total_matching",
          "browse_url",
          "note",
          "plans"
        ],
        "properties": {
          "country": {
            "$ref": "#/components/schemas/Country"
          },
          "trip_days": {
            "type": [
              "integer",
              "null"
            ],
            "minimum": 1,
            "maximum": 366
          },
          "currency": {
            "type": "string",
            "const": "USD"
          },
          "updated_at": {
            "type": "string",
            "format": "date-time",
            "description": "Country: upstream catalog snapshot time (five-minute cache). Regional: time the bundle catalog was retrieved; not a provider price-change timestamp."
          },
          "total_matching": {
            "type": "integer",
            "minimum": 0
          },
          "browse_url": {
            "type": "string",
            "format": "uri"
          },
          "note": {
            "type": "string"
          },
          "plans": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/Plan"
            }
          }
        },
        "additionalProperties": false
      },
      "RegionalSearch": {
        "type": "object",
        "required": [
          "requested_country_codes",
          "region",
          "trip_days",
          "currency",
          "updated_at",
          "total_matching",
          "browse_url",
          "note",
          "plans"
        ],
        "properties": {
          "requested_country_codes": {
            "type": "array",
            "items": {
              "type": "string",
              "pattern": "^[A-Za-z]{2}$",
              "description": "Assigned ISO alpha-2 code; catalog-supported XK is also accepted. Codes are case-insensitive."
            }
          },
          "region": {
            "type": [
              "string",
              "null"
            ]
          },
          "trip_days": {
            "type": [
              "integer",
              "null"
            ],
            "minimum": 1,
            "maximum": 366
          },
          "currency": {
            "type": "string",
            "const": "USD"
          },
          "updated_at": {
            "type": "string",
            "format": "date-time",
            "description": "Country: upstream catalog snapshot time (five-minute cache). Regional: time the bundle catalog was retrieved; not a provider price-change timestamp."
          },
          "total_matching": {
            "type": "integer",
            "minimum": 0
          },
          "browse_url": {
            "type": "string",
            "format": "uri"
          },
          "note": {
            "type": "string"
          },
          "plans": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/RegionalPlan"
            }
          }
        },
        "additionalProperties": false
      },
      "PlanDetail": {
        "type": "object",
        "required": [
          "country",
          "currency",
          "updated_at",
          "plan",
          "note"
        ],
        "properties": {
          "country": {
            "$ref": "#/components/schemas/Country"
          },
          "currency": {
            "type": "string",
            "const": "USD"
          },
          "updated_at": {
            "type": "string",
            "format": "date-time",
            "description": "Country: upstream catalog snapshot time (five-minute cache). Regional: time the bundle catalog was retrieved; not a provider price-change timestamp."
          },
          "plan": {
            "$ref": "#/components/schemas/Plan"
          },
          "note": {
            "type": "string"
          }
        },
        "additionalProperties": false
      },
      "Error": {
        "type": "object",
        "required": [
          "error"
        ],
        "properties": {
          "error": {
            "type": "object",
            "required": [
              "code",
              "message"
            ],
            "properties": {
              "code": {
                "type": "string"
              },
              "message": {
                "type": "string"
              },
              "details": {
                "type": "array",
                "items": {
                  "type": "object",
                  "required": [
                    "field",
                    "message"
                  ],
                  "properties": {
                    "field": {
                      "type": "string"
                    },
                    "message": {
                      "type": "string"
                    }
                  },
                  "additionalProperties": false
                }
              }
            },
            "additionalProperties": false
          }
        },
        "additionalProperties": false
      },
      "ComparisonPlan": {
        "type": "object",
        "required": [
          "id",
          "package_code",
          "name",
          "country_codes",
          "data_gb",
          "allowance_period",
          "is_unlimited",
          "allowance_behavior",
          "reduced_speed_kbps",
          "maximum_speed_kbps",
          "validity_days",
          "is_daily",
          "price_usd",
          "operators",
          "plan_page_url",
          "checkout_url"
        ],
        "properties": {
          "id": {
            "type": "string",
            "description": "Stable variant ID. Fixed plans use package_code; day-pass variants append --<days>d."
          },
          "package_code": {
            "type": "string",
            "pattern": "^[A-Za-z0-9_-]{1,100}$"
          },
          "name": {
            "type": "string"
          },
          "country_codes": {
            "type": "array",
            "minItems": 1,
            "uniqueItems": true,
            "items": {
              "type": "string",
              "pattern": "^[A-Z]{2}$"
            },
            "description": "Exact published coverage, not inferred from a region name."
          },
          "data_gb": {
            "type": [
              "number",
              "null"
            ],
            "minimum": 0,
            "description": "High-speed allowance in binary GB (1024^3 bytes) for allowance_period. This is not a total allowance for daily plans. Null for verified unlimited plans without a finite quota."
          },
          "allowance_period": {
            "type": [
              "string",
              "null"
            ],
            "enum": [
              "plan",
              "day",
              null
            ]
          },
          "is_unlimited": {
            "type": "boolean",
            "description": "True for daily throttled access and verified unlimited plans; inspect allowance_behavior and speed limits."
          },
          "allowance_behavior": {
            "type": "string",
            "enum": [
              "total",
              "daily_throttled",
              "daily_cutoff",
              "unlimited"
            ],
            "description": "daily_throttled continues at reduced_speed_kbps after each daily high-speed allowance; daily_cutoff stops data until the quota resets."
          },
          "reduced_speed_kbps": {
            "type": [
              "integer",
              "null"
            ],
            "minimum": 1,
            "description": "Verified post-quota speed for daily_throttled plans, otherwise null."
          },
          "maximum_speed_kbps": {
            "type": [
              "integer",
              "null"
            ],
            "minimum": 1,
            "description": "Verified initial speed cap if known; null means not specified, not uncapped."
          },
          "validity_days": {
            "type": "integer",
            "minimum": 1
          },
          "is_daily": {
            "type": "boolean",
            "description": "Selectable day pass, expanded into every purchasable duration from 1 to 90 days."
          },
          "price_usd": {
            "type": "number",
            "exclusiveMinimum": 0,
            "description": "Retail total for the selected duration using the same quote as checkout, before coupons."
          },
          "operators": {
            "type": "array",
            "items": {
              "type": "object",
              "required": [
                "name",
                "network"
              ],
              "properties": {
                "name": {
                  "type": "string"
                },
                "network": {
                  "type": [
                    "string",
                    "null"
                  ]
                }
              },
              "additionalProperties": false
            },
            "description": "Provider operator summary, not a per-country network map."
          },
          "plan_page_url": {
            "type": "string",
            "format": "uri"
          },
          "checkout_url": {
            "type": "string",
            "format": "uri",
            "description": "Opens checkout with periodNum for day passes. Does not place an order."
          }
        },
        "additionalProperties": false
      },
      "ComparisonCatalog": {
        "type": "object",
        "required": [
          "schema_version",
          "provider",
          "currency",
          "price_basis",
          "total_plans",
          "plans",
          "catalog_version",
          "generated_at",
          "source_updated_at",
          "refresh_after_seconds"
        ],
        "properties": {
          "schema_version": {
            "type": "integer",
            "const": 1
          },
          "provider": {
            "type": "string",
            "const": "AeroCell"
          },
          "currency": {
            "type": "string",
            "const": "USD"
          },
          "price_basis": {
            "type": "string"
          },
          "total_plans": {
            "type": "integer",
            "minimum": 0
          },
          "plans": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/ComparisonPlan"
            }
          },
          "catalog_version": {
            "type": "string",
            "pattern": "^[a-f0-9]{64}$",
            "description": "Hash of public plan content. Changes for prices, coverage, additions or removals."
          },
          "generated_at": {
            "type": "string",
            "format": "date-time",
            "description": "When this content version was generated, not a provider price-change time."
          },
          "source_updated_at": {
            "type": "string",
            "format": "date-time",
            "description": "Oldest provider catalog retrieval used in this snapshot. Expired provider data is rejected after 15 minutes."
          },
          "refresh_after_seconds": {
            "type": "integer",
            "const": 900
          }
        },
        "additionalProperties": false
      },
      "PartnerComparisonCatalog": {
        "type": "object",
        "required": [
          "schema_version",
          "provider",
          "currency",
          "price_basis",
          "total_plans",
          "plans",
          "catalog_version",
          "generated_at",
          "source_updated_at",
          "refresh_after_seconds",
          "tracking_enabled"
        ],
        "properties": {
          "schema_version": {
            "type": "integer",
            "const": 1
          },
          "provider": {
            "type": "string",
            "const": "AeroCell"
          },
          "currency": {
            "type": "string",
            "const": "USD"
          },
          "price_basis": {
            "type": "string"
          },
          "total_plans": {
            "type": "integer",
            "minimum": 0
          },
          "plans": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/ComparisonPlan"
            }
          },
          "catalog_version": {
            "type": "string",
            "pattern": "^[a-f0-9]{64}$",
            "description": "Hash of the underlying public catalog, before partner link decoration."
          },
          "generated_at": {
            "type": "string",
            "format": "date-time",
            "description": "When this content version was generated, not a provider price-change time."
          },
          "source_updated_at": {
            "type": "string",
            "format": "date-time",
            "description": "Oldest provider catalog retrieval used in this snapshot. Expired provider data is rejected after 15 minutes."
          },
          "refresh_after_seconds": {
            "type": "integer",
            "const": 900
          },
          "tracking_enabled": {
            "type": "boolean",
            "description": "Whether plan and checkout links carry the registered partner attribution parameter. Existing consent and purchase eligibility rules still apply."
          }
        },
        "additionalProperties": false
      }
    },
    "securitySchemes": {
      "partnerFeedKey": {
        "type": "http",
        "scheme": "bearer",
        "bearerFormat": "64-character hexadecimal scoped feed credential",
        "description": "Existing active partner feed key, fetched from your server. Does not authenticate purchases or reporting access."
      }
    }
  }
}
