{
  "openapi": "3.1.0",
  "info": {
    "title": "The Boss System API",
    "version": "1.0",
    "description": "Integraciones de agencias. Las claves son privadas y están ligadas a una agencia y empresa. Los endpoints B2C públicos se documentan por separado en la página."
  },
  "servers": [
    {
      "url": "https://backoffice.thebosscaribbeantravel.com/api/v1"
    }
  ],
  "paths": {
    "/services": {
      "get": {
        "summary": "Consultar catálogo de servicios",
        "tags": [
          "Agencias"
        ],
        "security": [
          {
            "ApiKey": []
          },
          {
            "BearerKey": []
          }
        ],
        "responses": {
          "200": {
            "description": "Consulta correcta"
          },
          "401": {
            "description": "Clave requerida, inválida o revocada"
          },
          "404": {
            "description": "Recurso no encontrado o fuera de tu agencia"
          },
          "422": {
            "description": "Datos no válidos"
          },
          "429": {
            "description": "Límite de solicitudes"
          }
        }
      }
    },
    "/transfer-catalog": {
      "get": {
        "summary": "Consultar zonas, aeropuertos, hoteles y tiempos",
        "tags": [
          "Agencias"
        ],
        "security": [
          {
            "ApiKey": []
          },
          {
            "BearerKey": []
          }
        ],
        "responses": {
          "200": {
            "description": "Consulta correcta"
          },
          "401": {
            "description": "Clave requerida, inválida o revocada"
          },
          "404": {
            "description": "Recurso no encontrado o fuera de tu agencia"
          },
          "422": {
            "description": "Datos no válidos"
          },
          "429": {
            "description": "Límite de solicitudes"
          }
        }
      }
    },
    "/orders": {
      "get": {
        "summary": "Listar reservas de la agencia",
        "tags": [
          "Agencias"
        ],
        "security": [
          {
            "ApiKey": []
          },
          {
            "BearerKey": []
          }
        ],
        "responses": {
          "200": {
            "description": "Consulta correcta"
          },
          "401": {
            "description": "Clave requerida, inválida o revocada"
          },
          "404": {
            "description": "Recurso no encontrado o fuera de tu agencia"
          },
          "422": {
            "description": "Datos no válidos"
          },
          "429": {
            "description": "Límite de solicitudes"
          }
        },
        "parameters": [
          {
            "name": "per_page",
            "in": "query",
            "schema": {
              "type": "integer",
              "minimum": 1,
              "maximum": 100,
              "default": 25
            }
          },
          {
            "name": "page",
            "in": "query",
            "schema": {
              "type": "integer",
              "minimum": 1
            }
          },
          {
            "name": "status",
            "in": "query",
            "schema": {
              "type": "string"
            }
          }
        ]
      },
      "post": {
        "summary": "Crear reserva",
        "tags": [
          "Agencias"
        ],
        "security": [
          {
            "ApiKey": []
          },
          {
            "BearerKey": []
          }
        ],
        "responses": {
          "200": {
            "description": "Consulta correcta"
          },
          "401": {
            "description": "Clave requerida, inválida o revocada"
          },
          "404": {
            "description": "Recurso no encontrado o fuera de tu agencia"
          },
          "422": {
            "description": "Datos no válidos"
          },
          "429": {
            "description": "Límite de solicitudes"
          },
          "201": {
            "description": "Recurso creado"
          }
        },
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/OrderInput"
              }
            }
          }
        }
      }
    },
    "/orders/{orderCode}": {
      "get": {
        "summary": "Consultar reserva y seguimiento",
        "tags": [
          "Agencias"
        ],
        "security": [
          {
            "ApiKey": []
          },
          {
            "BearerKey": []
          }
        ],
        "responses": {
          "200": {
            "description": "Consulta correcta"
          },
          "401": {
            "description": "Clave requerida, inválida o revocada"
          },
          "404": {
            "description": "Recurso no encontrado o fuera de tu agencia"
          },
          "422": {
            "description": "Datos no válidos"
          },
          "429": {
            "description": "Límite de solicitudes"
          }
        },
        "parameters": [
          {
            "name": "orderCode",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ]
      }
    },
    "/orders/{orderCode}/payments/aloha": {
      "get": {
        "summary": "Listar pagos Aloha Pay",
        "tags": [
          "Agencias"
        ],
        "security": [
          {
            "ApiKey": []
          },
          {
            "BearerKey": []
          }
        ],
        "responses": {
          "200": {
            "description": "Consulta correcta"
          },
          "401": {
            "description": "Clave requerida, inválida o revocada"
          },
          "404": {
            "description": "Recurso no encontrado o fuera de tu agencia"
          },
          "422": {
            "description": "Datos no válidos"
          },
          "429": {
            "description": "Límite de solicitudes"
          }
        },
        "parameters": [
          {
            "name": "orderCode",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ]
      }
    },
    "/orders/{orderCode}/payments/aloha/link": {
      "post": {
        "summary": "Crear o reutilizar enlace de pago",
        "tags": [
          "Agencias"
        ],
        "security": [
          {
            "ApiKey": []
          },
          {
            "BearerKey": []
          }
        ],
        "responses": {
          "200": {
            "description": "Consulta correcta"
          },
          "401": {
            "description": "Clave requerida, inválida o revocada"
          },
          "404": {
            "description": "Recurso no encontrado o fuera de tu agencia"
          },
          "422": {
            "description": "Datos no válidos"
          },
          "429": {
            "description": "Límite de solicitudes"
          },
          "201": {
            "description": "Recurso creado"
          }
        },
        "parameters": [
          {
            "name": "orderCode",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "Idempotency-Key",
            "in": "header",
            "schema": {
              "type": "string",
              "maxLength": 100,
              "pattern": "^[A-Za-z0-9._:-]+$"
            }
          }
        ],
        "requestBody": {
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "amount": {
                    "type": "number",
                    "minimum": 0.5
                  },
                  "success_url": {
                    "type": "string",
                    "format": "uri",
                    "description": "URL HTTPS"
                  },
                  "idempotency_key": {
                    "type": "string",
                    "maxLength": 100
                  }
                }
              }
            }
          }
        }
      }
    }
  },
  "components": {
    "securitySchemes": {
      "ApiKey": {
        "type": "apiKey",
        "in": "header",
        "name": "X-API-Key"
      },
      "BearerKey": {
        "type": "http",
        "scheme": "bearer",
        "description": "La misma clave API opaca; no es un JWT ni la contraseña del usuario."
      }
    },
    "schemas": {
      "OrderInput": {
        "type": "object",
        "required": [
          "customer_name",
          "travel_date",
          "travel_time",
          "passengers"
        ],
        "properties": {
          "service_code": {
            "type": "string",
            "description": "Código obtenido en GET /services"
          },
          "customer_name": {
            "type": "string",
            "maxLength": 180
          },
          "travel_date": {
            "type": "string",
            "format": "date"
          },
          "travel_time": {
            "type": "string",
            "pattern": "^(?:[01][0-9]|2[0-3]):[0-5][0-9]$"
          },
          "passengers": {
            "type": "integer",
            "minimum": 1
          },
          "customer_email": {
            "type": "string",
            "format": "email"
          },
          "customer_phone": {
            "type": "string",
            "maxLength": 80
          },
          "country_code": {
            "type": "string",
            "minLength": 2,
            "maxLength": 2
          },
          "order_type": {
            "type": "string",
            "enum": [
              "transfer",
              "excursion",
              "custom"
            ]
          },
          "client_reference": {
            "type": "string",
            "maxLength": 120
          },
          "hotel_name": {
            "type": "string",
            "maxLength": 180
          },
          "pickup_location": {
            "type": "string",
            "maxLength": 220
          },
          "dropoff_location": {
            "type": "string",
            "maxLength": 220
          },
          "quantity": {
            "type": "integer",
            "minimum": 1
          },
          "flight_number": {
            "type": "string",
            "maxLength": 90
          },
          "promo_code": {
            "type": "string",
            "maxLength": 60
          },
          "client_notes": {
            "type": "string"
          },
          "luggage_suitcases": {
            "type": "integer",
            "minimum": 0
          },
          "luggage_handbags": {
            "type": "integer",
            "minimum": 0
          },
          "children_under_one": {
            "type": "integer",
            "minimum": 0
          },
          "children_over_one": {
            "type": "integer",
            "minimum": 0
          },
          "baby_seat_count": {
            "type": "integer",
            "minimum": 0
          }
        }
      }
    }
  }
}